From b2a23bdf893a3458bc967f6d805c5301019a6ce2 Mon Sep 17 00:00:00 2001
From: DahoudG <41957584+DahoudG@users.noreply.github.com>
Date: Wed, 20 Aug 2025 21:00:35 +0000
Subject: [PATCH] first commit
---
.gitignore | 30 +
pom.xml | 42 +
.../pom.xml | 210 +
.../client/UnionFlowClientApplication.java | 34 +
.../client/converter/MembreConverter.java | 43 +
.../unionflow/client/dto/AssociationDTO.java | 177 +
.../unionflow/client/dto/FormulaireDTO.java | 180 +
.../lions/unionflow/client/dto/MembreDTO.java | 187 +
.../unionflow/client/dto/SouscriptionDTO.java | 240 +
.../client/dto/auth/LoginRequest.java | 60 +
.../client/dto/auth/LoginResponse.java | 223 +
.../ViewExpiredExceptionHandler.java | 87 +
.../ViewExpiredExceptionHandlerFactory.java | 18 +
.../client/security/AuthenticationFilter.java | 89 +
.../security/JwtClientRequestFilter.java | 39 +
.../client/security/JwtTokenManager.java | 129 +
.../client/security/PermissionChecker.java | 239 +
.../client/security/TokenCleanupService.java | 26 +
.../client/security/TokenRefreshService.java | 150 +
.../client/service/AssociationService.java | 167 +
.../client/service/AuthenticationService.java | 170 +
.../client/service/MembreService.java | 165 +
.../service/RestClientExceptionMapper.java | 86 +
.../client/service/ValidationService.java | 102 +
.../validation/MemberNumberValidator.java | 51 +
.../validation/PhoneNumberValidator.java | 46 +
.../client/validation/ValidMemberNumber.java | 18 +
.../client/validation/ValidPhoneNumber.java | 18 +
.../client/validation/ValidationGroups.java | 47 +
.../client/view/AdminFormulaireBean.java | 344 +
.../unionflow/client/view/AuditBean.java | 454 +
.../client/view/ConfigurationBean.java | 730 ++
.../client/view/CotisationsBean.java | 691 ++
.../client/view/CotisationsGestionBean.java | 699 ++
.../unionflow/client/view/DashboardBean.java | 349 +
.../client/view/DemandesAideBean.java | 638 ++
.../unionflow/client/view/DemandesBean.java | 463 +
.../unionflow/client/view/DocumentsBean.java | 690 ++
.../client/view/EntitesGestionBean.java | 706 ++
.../unionflow/client/view/EvenementsBean.java | 588 ++
.../unionflow/client/view/FormulaireBean.java | 261 +
.../client/view/GuestPreferences.java | 146 +
.../unionflow/client/view/GuideBean.java | 241 +
.../unionflow/client/view/HelloView.java | 48 +
.../unionflow/client/view/LoginBean.java | 201 +
.../client/view/MembreCotisationBean.java | 441 +
.../client/view/MembreDashboardBean.java | 410 +
.../client/view/MembreInscriptionBean.java | 454 +
.../client/view/MembreListeBean.java | 324 +
.../client/view/MembreProfilBean.java | 742 ++
.../client/view/MembreRechercheBean.java | 717 ++
.../unionflow/client/view/NavigationBean.java | 135 +
.../unionflow/client/view/RapportsBean.java | 736 ++
.../unionflow/client/view/RolesBean.java | 426 +
.../client/view/SecurityStatusBean.java | 109 +
.../client/view/SouscriptionBean.java | 256 +
.../unionflow/client/view/SuperAdminBean.java | 633 ++
.../unionflow/client/view/UserSession.java | 297 +
.../client/view/UtilisateursBean.java | 444 +
.../main/resources/META-INF/faces-config.xml | 22 +
.../META-INF/resources/css/layout-dark.css | 4257 +++++++++
.../META-INF/resources/css/layout-dark.scss | 5 +
.../META-INF/resources/css/layout-light.css | 4257 +++++++++
.../META-INF/resources/css/layout-light.scss | 5 +
.../resources/css/primeflex-v2.min.css | 1 +
.../META-INF/resources/css/primeflex.min.css | 1 +
.../META-INF/resources/css/primeicons.css | 1017 +++
.../resources/error/viewExpired.xhtml | 77 +
.../freya-layout/css/layout-dark.css | 4257 +++++++++
.../freya-layout/css/layout-dark.scss | 5 +
.../freya-layout/css/layout-light.css | 4257 +++++++++
.../freya-layout/css/layout-light.scss | 5 +
.../freya-layout/css/primeflex-v2.min.css | 1 +
.../freya-layout/css/primeflex.min.css | 1 +
.../resources/freya-layout/css/primeicons.css | 1017 +++
.../freya-layout/icons/primeicons.eot | Bin 0 -> 66820 bytes
.../freya-layout/icons/primeicons.svg | 270 +
.../freya-layout/icons/primeicons.ttf | Bin 0 -> 66644 bytes
.../freya-layout/icons/primeicons.woff | Bin 0 -> 66720 bytes
.../images/avatar-profilemenu.png | Bin 0 -> 1249 bytes
.../resources/freya-layout/images/favicon.ico | Bin 0 -> 15086 bytes
.../freya-layout/images/logo-freya-single.svg | 9 +
.../freya-layout/images/logo-freya-white.svg | 14 +
.../freya-layout/images/logo-freya.svg | 40 +
.../freya-layout/images/pages/asset-404.svg | 9 +
.../images/pages/asset-access.svg | 9 +
.../freya-layout/images/pages/asset-error.svg | 9 +
.../images/pages/asset-landing-header.jpg | Bin 0 -> 844761 bytes
.../freya-layout/images/pages/search.png | Bin 0 -> 788 bytes
.../resources/freya-layout/js/layout.js | 879 ++
.../resources/freya-layout/js/prism.js | 10 +
.../META-INF/resources/icons/primeicons.eot | Bin 0 -> 66820 bytes
.../META-INF/resources/icons/primeicons.svg | 270 +
.../META-INF/resources/icons/primeicons.ttf | Bin 0 -> 66644 bytes
.../META-INF/resources/icons/primeicons.woff | Bin 0 -> 66720 bytes
.../resources/images/avatar-profilemenu.png | Bin 0 -> 1249 bytes
.../META-INF/resources/images/favicon.ico | Bin 0 -> 15086 bytes
.../resources/images/logo-freya-single.svg | 9 +
.../resources/images/logo-freya-white.svg | 14 +
.../META-INF/resources/images/logo-freya.svg | 40 +
.../resources/images/pages/asset-404.svg | 9 +
.../resources/images/pages/asset-access.svg | 9 +
.../resources/images/pages/asset-error.svg | 9 +
.../images/pages/asset-landing-header.jpg | Bin 0 -> 844761 bytes
.../resources/images/pages/search.png | Bin 0 -> 788 bytes
.../resources/META-INF/resources/index.xhtml | 173 +
.../resources/META-INF/resources/js/layout.js | 879 ++
.../resources/META-INF/resources/js/prism.js | 10 +
.../resources/pages/admin/aides/gestion.xhtml | 595 ++
.../resources/pages/admin/audit.xhtml | 20 +
.../resources/pages/admin/audit/journal.xhtml | 422 +
.../resources/pages/admin/backup.xhtml | 20 +
.../pages/admin/cotisations/gestion.xhtml | 786 ++
.../pages/admin/demandes/aide-sociale.xhtml | 558 ++
.../pages/admin/demandes/gestion-old.xhtml | 561 ++
.../pages/admin/demandes/gestion.xhtml | 651 ++
.../pages/admin/documents/gestion.xhtml | 613 ++
.../pages/admin/evenements/creation.xhtml | 541 ++
.../pages/admin/evenements/gestion.xhtml | 622 ++
.../pages/admin/evenements/liste.xhtml | 430 +
.../pages/admin/evenements/participants.xhtml | 517 ++
.../pages/admin/finance/caisse.xhtml | 409 +
.../pages/admin/rapports/finances.xhtml | 445 +
.../pages/admin/rapports/statistiques.xhtml | 574 ++
.../resources/pages/admin/settings.xhtml | 20 +
.../resources/pages/admin/users.xhtml | 20 +
.../pages/admin/utilisateurs/gestion.xhtml | 398 +
.../resources/pages/membre/cotisations.xhtml | 575 ++
.../resources/pages/membre/dashboard.xhtml | 385 +
.../resources/pages/public/formulaires.xhtml | 294 +
.../resources/pages/public/home.xhtml | 98 +
.../resources/pages/public/login.xhtml | 214 +
.../pages/secure/access-denied.xhtml | 55 +
.../pages/secure/adhesion/demande.xhtml | 43 +
.../pages/secure/adhesion/history.xhtml | 20 +
.../pages/secure/adhesion/liste.xhtml | 33 +
.../resources/pages/secure/adhesion/new.xhtml | 20 +
.../pages/secure/adhesion/pending.xhtml | 20 +
.../secure/adhesion/renouvellement.xhtml | 43 +
.../pages/secure/adhesion/validation.xhtml | 33 +
.../resources/pages/secure/admin/audit.xhtml | 21 +
.../pages/secure/admin/parametres.xhtml | 21 +
.../resources/pages/secure/admin/roles.xhtml | 21 +
.../pages/secure/admin/sauvegarde.xhtml | 21 +
.../pages/secure/admin/utilisateurs.xhtml | 21 +
.../pages/secure/aide/approved.xhtml | 20 +
.../resources/pages/secure/aide/apropos.xhtml | 326 +
.../resources/pages/secure/aide/demande.xhtml | 21 +
.../pages/secure/aide/documentation.xhtml | 169 +
.../resources/pages/secure/aide/faq.xhtml | 468 +
.../resources/pages/secure/aide/guide.xhtml | 406 +
.../pages/secure/aide/historique.xhtml | 21 +
.../resources/pages/secure/aide/history.xhtml | 20 +
.../pages/secure/aide/nouveautes.xhtml | 400 +
.../pages/secure/aide/requests.xhtml | 20 +
.../pages/secure/aide/statistiques.xhtml | 21 +
.../pages/secure/aide/suggestions.xhtml | 462 +
.../resources/pages/secure/aide/support.xhtml | 321 +
.../resources/pages/secure/aide/tickets.xhtml | 436 +
.../pages/secure/aide/traitement.xhtml | 21 +
.../pages/secure/aide/tutoriels.xhtml | 367 +
.../pages/secure/cotisation/collect.xhtml | 20 +
.../pages/secure/cotisation/historique.xhtml | 21 +
.../pages/secure/cotisation/paiement.xhtml | 21 +
.../pages/secure/cotisation/rapports.xhtml | 21 +
.../pages/secure/cotisation/relances.xhtml | 21 +
.../pages/secure/cotisation/reminders.xhtml | 20 +
.../pages/secure/cotisation/report.xhtml | 20 +
.../resources/pages/secure/dashboard.xhtml | 552 ++
.../pages/secure/evenement/calendar.xhtml | 20 +
.../pages/secure/evenement/calendrier.xhtml | 21 +
.../pages/secure/evenement/create.xhtml | 20 +
.../pages/secure/evenement/creation.xhtml | 21 +
.../pages/secure/evenement/gestion.xhtml | 21 +
.../pages/secure/evenement/participants.xhtml | 20 +
.../secure/evenement/participation.xhtml | 21 +
.../pages/secure/membre/inscription.xhtml | 719 ++
.../resources/pages/secure/membre/list.xhtml | 26 +
.../resources/pages/secure/membre/liste.xhtml | 467 +
.../resources/pages/secure/membre/new.xhtml | 26 +
.../pages/secure/membre/profil.xhtml | 628 ++
.../pages/secure/membre/recherche.xhtml | 701 ++
.../pages/secure/membre/search.xhtml | 20 +
.../pages/secure/personnel/activites.xhtml | 425 +
.../pages/secure/personnel/agenda.xhtml | 636 ++
.../pages/secure/personnel/documents.xhtml | 600 ++
.../pages/secure/personnel/favoris.xhtml | 520 ++
.../secure/personnel/notifications.xhtml | 428 +
.../pages/secure/personnel/parametres.xhtml | 703 ++
.../pages/secure/personnel/preferences.xhtml | 490 ++
.../pages/secure/personnel/profil.xhtml | 401 +
.../resources/pages/secure/profile.xhtml | 241 +
.../pages/secure/rapport/activites.xhtml | 21 +
.../pages/secure/rapport/export.xhtml | 21 +
.../pages/secure/rapport/finances.xhtml | 21 +
.../pages/secure/rapport/membres.xhtml | 21 +
.../resources/pages/secure/reports.xhtml | 26 +
.../pages/secure/souscription/dashboard.xhtml | 355 +
.../resources/pages/secure/stats.xhtml | 26 +
.../pages/super-admin/configuration.xhtml | 775 ++
.../super-admin/configuration/systeme.xhtml | 764 ++
.../super-admin/dashboard-enhanced.xhtml | 375 +
.../pages/super-admin/dashboard.xhtml | 523 ++
.../entites/gestion-enhanced.xhtml | 641 ++
.../pages/super-admin/entites/gestion.xhtml | 468 +
.../pages/super-admin/roles/gestion.xhtml | 381 +
.../primefaces-freya-avocado-dark/theme.css | 7711 +++++++++++++++++
.../primefaces-freya-avocado-dark/theme.scss | 9 +
.../primefaces-freya-avocado-light/theme.css | 7710 ++++++++++++++++
.../primefaces-freya-avocado-light/theme.scss | 9 +
.../primefaces-freya-blue-dark/theme.css | 7711 +++++++++++++++++
.../primefaces-freya-blue-dark/theme.scss | 9 +
.../primefaces-freya-blue-light/theme.css | 7710 ++++++++++++++++
.../primefaces-freya-blue-light/theme.scss | 9 +
.../primefaces-freya-green-dark/theme.css | 7711 +++++++++++++++++
.../primefaces-freya-green-dark/theme.scss | 9 +
.../primefaces-freya-green-light/theme.css | 7710 ++++++++++++++++
.../primefaces-freya-green-light/theme.scss | 9 +
.../primefaces-freya-orange-dark/theme.css | 7711 +++++++++++++++++
.../primefaces-freya-orange-dark/theme.scss | 9 +
.../primefaces-freya-orange-light/theme.css | 7710 ++++++++++++++++
.../primefaces-freya-orange-light/theme.scss | 9 +
.../primefaces-freya-purple-dark/theme.css | 7711 +++++++++++++++++
.../primefaces-freya-purple-dark/theme.scss | 9 +
.../primefaces-freya-purple-light/theme.css | 7710 ++++++++++++++++
.../primefaces-freya-purple-light/theme.scss | 9 +
.../primefaces-freya-red-dark/theme.css | 7711 +++++++++++++++++
.../primefaces-freya-red-dark/theme.scss | 9 +
.../primefaces-freya-red-light/theme.css | 7710 ++++++++++++++++
.../primefaces-freya-red-light/theme.scss | 9 +
.../primefaces-freya-turquoise-dark/theme.css | 7711 +++++++++++++++++
.../theme.scss | 9 +
.../theme.css | 7710 ++++++++++++++++
.../theme.scss | 9 +
.../primefaces-freya-yellow-dark/theme.css | 7711 +++++++++++++++++
.../primefaces-freya-yellow-dark/theme.scss | 9 +
.../primefaces-freya-yellow-light/theme.css | 7710 ++++++++++++++++
.../primefaces-freya-yellow-light/theme.scss | 9 +
.../resources/resources/demo/chartjs/chart.js | 10 +
.../resources/demo/css/_demo_common.scss | 13 +
.../resources/demo/css/demo-dark.css | 734 ++
.../resources/demo/css/demo-dark.scss | 3 +
.../resources/demo/css/demo-light.css | 734 ++
.../resources/demo/css/demo-light.scss | 2 +
.../resources/demo/css/flags/flags.css | 1 +
.../demo/css/flags/flags_responsive.png | Bin 0 -> 55194 bytes
.../resources/demo/css/pages/_blocks.scss | 133 +
.../resources/demo/css/pages/_chronoline.scss | 33 +
.../resources/demo/css/pages/_common.scss | 122 +
.../resources/demo/css/pages/_crud.scss | 68 +
.../demo/css/pages/_documentation.scss | 3 +
.../resources/demo/css/pages/_floatlabel.scss | 5 +
.../resources/demo/css/pages/_icons.scss | 11 +
.../resources/demo/css/pages/_list.scss | 120 +
.../resources/demo/css/pages/_messages.scss | 9 +
.../resources/demo/css/pages/_misc.scss | 39 +
.../resources/demo/css/pages/_syntax.scss | 244 +
.../resources/demo/css/pages/_table.scss | 21 +
.../demo/images/avatar/amyelsner.png | Bin 0 -> 5257 bytes
.../resources/demo/images/avatar/annafali.png | Bin 0 -> 5612 bytes
.../demo/images/avatar/asiyajavayant.png | Bin 0 -> 5597 bytes
.../demo/images/avatar/bernardodominic.png | Bin 0 -> 5870 bytes
.../demo/images/avatar/elwinsharvill.png | Bin 0 -> 5588 bytes
.../demo/images/avatar/ionibowcher.png | Bin 0 -> 5731 bytes
.../demo/images/avatar/ivanmagalhaes.png | Bin 0 -> 6088 bytes
.../demo/images/avatar/onyamalimba.png | Bin 0 -> 5422 bytes
.../resources/demo/images/avatar/profile.jpg | Bin 0 -> 8051 bytes
.../demo/images/avatar/stephenshaw.png | Bin 0 -> 5227 bytes
.../demo/images/avatar/xuxuefeng.png | Bin 0 -> 6057 bytes
.../demo/images/blocks/hero/hero-1.png | Bin 0 -> 654997 bytes
.../demo/images/blocks/logos/hyper.svg | 3 +
.../resources/demo/images/car/Audi.png | Bin 0 -> 6685 bytes
.../resources/demo/images/car/BMW.png | Bin 0 -> 8406 bytes
.../resources/demo/images/car/Fiat.png | Bin 0 -> 9903 bytes
.../resources/demo/images/car/Ford.png | Bin 0 -> 8540 bytes
.../resources/demo/images/car/Honda.png | Bin 0 -> 5037 bytes
.../resources/demo/images/car/Jaguar.png | Bin 0 -> 13310 bytes
.../resources/demo/images/car/Mercedes.png | Bin 0 -> 6071 bytes
.../resources/demo/images/car/Renault.png | Bin 0 -> 5694 bytes
.../resources/demo/images/car/Volkswagen.png | Bin 0 -> 10802 bytes
.../resources/demo/images/car/Volvo.png | Bin 0 -> 8198 bytes
.../demo/images/dashboard/asset-image.jpg | Bin 0 -> 87660 bytes
.../demo/images/dashboard/asset-map.png | Bin 0 -> 50643 bytes
.../demo/images/dashboard/avatar/avatar-1.png | Bin 0 -> 2303 bytes
.../demo/images/dashboard/avatar/avatar-2.png | Bin 0 -> 1997 bytes
.../demo/images/dashboard/avatar/avatar-3.png | Bin 0 -> 2549 bytes
.../demo/images/dashboard/avatar/avatar-4.png | Bin 0 -> 1526 bytes
.../demo/images/dashboard/avatar/avatar-5.png | Bin 0 -> 1477 bytes
.../demo/images/dashboard/avatar/avatar-6.png | Bin 0 -> 2313 bytes
.../demo/images/dashboard/avatar/avatar-7.png | Bin 0 -> 2271 bytes
.../demo/images/dashboard/mini-graph-1.svg | 10 +
.../demo/images/dashboard/mini-graph-2.svg | 10 +
.../demo/images/dashboard/mini-graph-3.svg | 10 +
.../demo/images/dashboard/mini-graph-4.svg | 10 +
.../demo/images/dashboard/mini-graph-5.svg | 10 +
.../demo/images/dashboard/subtract.svg | 9 +
.../demo/images/galleria/galleria1.jpg | Bin 0 -> 87135 bytes
.../demo/images/galleria/galleria10.jpg | Bin 0 -> 84662 bytes
.../demo/images/galleria/galleria10s.jpg | Bin 0 -> 2063 bytes
.../demo/images/galleria/galleria11.jpg | Bin 0 -> 64452 bytes
.../demo/images/galleria/galleria11s.jpg | Bin 0 -> 1627 bytes
.../demo/images/galleria/galleria12.jpg | Bin 0 -> 87325 bytes
.../demo/images/galleria/galleria12s.jpg | Bin 0 -> 1570 bytes
.../demo/images/galleria/galleria13.jpg | Bin 0 -> 104784 bytes
.../demo/images/galleria/galleria13s.jpg | Bin 0 -> 2086 bytes
.../demo/images/galleria/galleria14.jpg | Bin 0 -> 125110 bytes
.../demo/images/galleria/galleria14s.jpg | Bin 0 -> 2086 bytes
.../demo/images/galleria/galleria15.jpg | Bin 0 -> 111269 bytes
.../demo/images/galleria/galleria15s.jpg | Bin 0 -> 2661 bytes
.../demo/images/galleria/galleria1s.jpg | Bin 0 -> 2593 bytes
.../demo/images/galleria/galleria2.jpg | Bin 0 -> 95483 bytes
.../demo/images/galleria/galleria2s.jpg | Bin 0 -> 1572 bytes
.../demo/images/galleria/galleria3.jpg | Bin 0 -> 70886 bytes
.../demo/images/galleria/galleria3s.jpg | Bin 0 -> 2128 bytes
.../demo/images/galleria/galleria4.jpg | Bin 0 -> 124223 bytes
.../demo/images/galleria/galleria4s.jpg | Bin 0 -> 2266 bytes
.../demo/images/galleria/galleria5.jpg | Bin 0 -> 107127 bytes
.../demo/images/galleria/galleria5s.jpg | Bin 0 -> 2131 bytes
.../demo/images/galleria/galleria6.jpg | Bin 0 -> 28732 bytes
.../demo/images/galleria/galleria6s.jpg | Bin 0 -> 1009 bytes
.../demo/images/galleria/galleria7.jpg | Bin 0 -> 49048 bytes
.../demo/images/galleria/galleria7s.jpg | Bin 0 -> 1395 bytes
.../demo/images/galleria/galleria8.jpg | Bin 0 -> 119967 bytes
.../demo/images/galleria/galleria8s.jpg | Bin 0 -> 2421 bytes
.../demo/images/galleria/galleria9.jpg | Bin 0 -> 95881 bytes
.../demo/images/galleria/galleria9s.jpg | Bin 0 -> 2331 bytes
.../resources/demo/images/nature/nature.jpg | Bin 0 -> 95677 bytes
.../demo/images/product/bamboo-watch.jpg | Bin 0 -> 10104 bytes
.../demo/images/product/black-watch.jpg | Bin 0 -> 9942 bytes
.../demo/images/product/blue-band.jpg | Bin 0 -> 3199 bytes
.../demo/images/product/blue-t-shirt.jpg | Bin 0 -> 7577 bytes
.../demo/images/product/bracelet.jpg | Bin 0 -> 4741 bytes
.../demo/images/product/brown-purse.jpg | Bin 0 -> 5720 bytes
.../demo/images/product/chakra-bracelet.jpg | Bin 0 -> 4587 bytes
.../demo/images/product/galaxy-earrings.jpg | Bin 0 -> 3208 bytes
.../demo/images/product/game-controller.jpg | Bin 0 -> 3982 bytes
.../demo/images/product/gaming-set.jpg | Bin 0 -> 9530 bytes
.../demo/images/product/gold-phone-case.jpg | Bin 0 -> 7818 bytes
.../demo/images/product/green-earbuds.jpg | Bin 0 -> 6996 bytes
.../demo/images/product/green-t-shirt.jpg | Bin 0 -> 7263 bytes
.../demo/images/product/grey-t-shirt.jpg | Bin 0 -> 7330 bytes
.../demo/images/product/headphones.jpg | Bin 0 -> 4497 bytes
.../images/product/light-green-t-shirt.jpg | Bin 0 -> 7347 bytes
.../demo/images/product/lime-band.jpg | Bin 0 -> 3212 bytes
.../demo/images/product/mini-speakers.jpg | Bin 0 -> 3684 bytes
.../images/product/painted-phone-case.jpg | Bin 0 -> 9455 bytes
.../demo/images/product/pink-band.jpg | Bin 0 -> 3093 bytes
.../demo/images/product/pink-purse.jpg | Bin 0 -> 4668 bytes
.../demo/images/product/purple-band.jpg | Bin 0 -> 3336 bytes
.../product/purple-gemstone-necklace.jpg | Bin 0 -> 3084 bytes
.../demo/images/product/purple-t-shirt.jpg | Bin 0 -> 7522 bytes
.../resources/demo/images/product/shoes.jpg | Bin 0 -> 6855 bytes
.../demo/images/product/sneakers.jpg | Bin 0 -> 7067 bytes
.../demo/images/product/teal-t-shirt.jpg | Bin 0 -> 7498 bytes
.../demo/images/product/yellow-earbuds.jpg | Bin 0 -> 7173 bytes
.../demo/images/product/yoga-mat.jpg | Bin 0 -> 6918 bytes
.../demo/images/product/yoga-set.jpg | Bin 0 -> 5133 bytes
.../demo/images/rightpanel/asset-weather.png | Bin 0 -> 40190 bytes
.../resources/demo/images/rightpanel/aws.svg | 11 +
.../demo/images/rightpanel/github.svg | 9 +
.../demo/images/rightpanel/icon-sun.svg | 3 +
.../demo/images/rightpanel/jenkins.svg | 9 +
.../resources/demo/images/rightpanel/jira.svg | 9 +
.../demo/images/rightpanel/profile-1.png | Bin 0 -> 5412 bytes
.../demo/images/rightpanel/profile-2.png | Bin 0 -> 6057 bytes
.../demo/images/rightpanel/profile-3.png | Bin 0 -> 7887 bytes
.../demo/images/rightpanel/profile-4.png | Bin 0 -> 3514 bytes
.../demo/images/rightpanel/slack.svg | 9 +
.../freya-layout/css/layout-dark.css | 4257 +++++++++
.../freya-layout/css/layout-dark.scss | 5 +
.../freya-layout/css/layout-light.css | 4257 +++++++++
.../freya-layout/css/layout-light.scss | 5 +
.../freya-layout/css/primeflex-v2.min.css | 1 +
.../freya-layout/css/primeflex.min.css | 1 +
.../resources/freya-layout/css/primeicons.css | 1017 +++
.../freya-layout/icons/primeicons.eot | Bin 0 -> 66820 bytes
.../freya-layout/icons/primeicons.svg | 270 +
.../freya-layout/icons/primeicons.ttf | Bin 0 -> 66644 bytes
.../freya-layout/icons/primeicons.woff | Bin 0 -> 66720 bytes
.../images/avatar-profilemenu.png | Bin 0 -> 1249 bytes
.../resources/freya-layout/images/favicon.ico | Bin 0 -> 15086 bytes
.../freya-layout/images/logo-freya-single.svg | 9 +
.../freya-layout/images/logo-freya-white.svg | 14 +
.../freya-layout/images/logo-freya.svg | 40 +
.../freya-layout/images/pages/asset-404.svg | 9 +
.../images/pages/asset-access.svg | 9 +
.../freya-layout/images/pages/asset-error.svg | 9 +
.../images/pages/asset-landing-header.jpg | Bin 0 -> 844761 bytes
.../freya-layout/images/pages/search.png | Bin 0 -> 788 bytes
.../resources/freya-layout/js/layout.js | 879 ++
.../resources/freya-layout/js/prism.js | 10 +
.../templates/components/config.xhtml | 93 +
.../templates/components/footer.xhtml | 57 +
.../resources/templates/components/menu.xhtml | 183 +
.../templates/components/rightpanel.xhtml | 187 +
.../templates/components/topbar.xhtml | 107 +
.../resources/templates/main-template.xhtml | 54 +
.../resources/templates/public-template.xhtml | 45 +
.../resources/ValidationMessages.properties | 37 +
.../src/main/resources/application.properties | 93 +
.../src/main/webapp/WEB-INF/beans.xml | 7 +
.../src/main/webapp/WEB-INF/faces-config.xml | 21 +
.../WEB-INF/primefaces-freya.taglib.xml | 65 +
.../src/main/webapp/WEB-INF/web.xml | 104 +
.../main/webapp/resources/css/layout-dark.css | 4257 +++++++++
.../webapp/resources/css/layout-dark.scss | 5 +
.../webapp/resources/css/layout-light.css | 4257 +++++++++
.../webapp/resources/css/layout-light.scss | 5 +
.../webapp/resources/css/primeflex-v2.min.css | 1 +
.../webapp/resources/css/primeflex.min.css | 1 +
.../main/webapp/resources/css/primeicons.css | 1017 +++
.../webapp/resources/icons/primeicons.eot | Bin 0 -> 66820 bytes
.../webapp/resources/icons/primeicons.svg | 270 +
.../webapp/resources/icons/primeicons.ttf | Bin 0 -> 66644 bytes
.../webapp/resources/icons/primeicons.woff | Bin 0 -> 66720 bytes
.../resources/images/avatar-profilemenu.png | Bin 0 -> 1249 bytes
.../main/webapp/resources/images/favicon.ico | Bin 0 -> 15086 bytes
.../resources/images/logo-freya-single.svg | 9 +
.../resources/images/logo-freya-white.svg | 14 +
.../webapp/resources/images/logo-freya.svg | 40 +
.../resources/images/pages/asset-404.svg | 9 +
.../resources/images/pages/asset-access.svg | 9 +
.../resources/images/pages/asset-error.svg | 9 +
.../images/pages/asset-landing-header.jpg | Bin 0 -> 844761 bytes
.../webapp/resources/images/pages/search.png | Bin 0 -> 788 bytes
.../src/main/webapp/resources/js/layout.js | 879 ++
.../src/main/webapp/resources/js/prism.js | 10 +
.../primefaces-freya-blue-light/theme.css | 7710 ++++++++++++++++
.../primefaces-freya-blue-light/theme.scss | 9 +
unionflow-mobile-apps/.gitignore | 43 +
unionflow-mobile-apps/.metadata | 33 +
unionflow-mobile-apps/README.md | 52 +
unionflow-mobile-apps/README_DEMARRAGE.md | 182 +
unionflow-mobile-apps/analysis_options.yaml | 28 +
unionflow-mobile-apps/android/.gitignore | 13 +
.../android/app/build.gradle | 44 +
.../android/app/src/debug/AndroidManifest.xml | 7 +
.../android/app/src/main/AndroidManifest.xml | 45 +
.../unionflow_mobile_apps/MainActivity.kt | 5 +
.../res/drawable-v21/launch_background.xml | 12 +
.../main/res/drawable/launch_background.xml | 12 +
.../src/main/res/mipmap-hdpi/ic_launcher.png | Bin 0 -> 544 bytes
.../src/main/res/mipmap-mdpi/ic_launcher.png | Bin 0 -> 442 bytes
.../src/main/res/mipmap-xhdpi/ic_launcher.png | Bin 0 -> 721 bytes
.../main/res/mipmap-xxhdpi/ic_launcher.png | Bin 0 -> 1031 bytes
.../main/res/mipmap-xxxhdpi/ic_launcher.png | Bin 0 -> 1443 bytes
.../app/src/main/res/values-night/styles.xml | 18 +
.../app/src/main/res/values/styles.xml | 18 +
.../app/src/profile/AndroidManifest.xml | 7 +
unionflow-mobile-apps/android/build.gradle | 39 +
.../android/gradle.properties | 15 +
.../gradle/wrapper/gradle-wrapper.properties | 5 +
unionflow-mobile-apps/android/settings.gradle | 25 +
unionflow-mobile-apps/fix-gradle-build.ps1 | 116 +
unionflow-mobile-apps/fix-gradle-build.sh | 62 +
unionflow-mobile-apps/fix_and_run.ps1 | 41 +
unionflow-mobile-apps/install_and_test.ps1 | 34 +
unionflow-mobile-apps/install_and_test.sh | 36 +
unionflow-mobile-apps/ios/.gitignore | 34 +
.../ios/Flutter/AppFrameworkInfo.plist | 26 +
.../ios/Flutter/Debug.xcconfig | 1 +
.../ios/Flutter/Release.xcconfig | 1 +
.../ios/Runner.xcodeproj/project.pbxproj | 616 ++
.../contents.xcworkspacedata | 7 +
.../xcshareddata/IDEWorkspaceChecks.plist | 8 +
.../xcshareddata/WorkspaceSettings.xcsettings | 8 +
.../xcshareddata/xcschemes/Runner.xcscheme | 98 +
.../contents.xcworkspacedata | 7 +
.../xcshareddata/IDEWorkspaceChecks.plist | 8 +
.../xcshareddata/WorkspaceSettings.xcsettings | 8 +
.../ios/Runner/AppDelegate.swift | 13 +
.../AppIcon.appiconset/Contents.json | 122 +
.../Icon-App-1024x1024@1x.png | Bin 0 -> 10932 bytes
.../AppIcon.appiconset/Icon-App-20x20@1x.png | Bin 0 -> 295 bytes
.../AppIcon.appiconset/Icon-App-20x20@2x.png | Bin 0 -> 406 bytes
.../AppIcon.appiconset/Icon-App-20x20@3x.png | Bin 0 -> 450 bytes
.../AppIcon.appiconset/Icon-App-29x29@1x.png | Bin 0 -> 282 bytes
.../AppIcon.appiconset/Icon-App-29x29@2x.png | Bin 0 -> 462 bytes
.../AppIcon.appiconset/Icon-App-29x29@3x.png | Bin 0 -> 704 bytes
.../AppIcon.appiconset/Icon-App-40x40@1x.png | Bin 0 -> 406 bytes
.../AppIcon.appiconset/Icon-App-40x40@2x.png | Bin 0 -> 586 bytes
.../AppIcon.appiconset/Icon-App-40x40@3x.png | Bin 0 -> 862 bytes
.../AppIcon.appiconset/Icon-App-60x60@2x.png | Bin 0 -> 862 bytes
.../AppIcon.appiconset/Icon-App-60x60@3x.png | Bin 0 -> 1674 bytes
.../AppIcon.appiconset/Icon-App-76x76@1x.png | Bin 0 -> 762 bytes
.../AppIcon.appiconset/Icon-App-76x76@2x.png | Bin 0 -> 1226 bytes
.../Icon-App-83.5x83.5@2x.png | Bin 0 -> 1418 bytes
.../LaunchImage.imageset/Contents.json | 23 +
.../LaunchImage.imageset/LaunchImage.png | Bin 0 -> 68 bytes
.../LaunchImage.imageset/LaunchImage@2x.png | Bin 0 -> 68 bytes
.../LaunchImage.imageset/LaunchImage@3x.png | Bin 0 -> 68 bytes
.../LaunchImage.imageset/README.md | 5 +
.../Runner/Base.lproj/LaunchScreen.storyboard | 37 +
.../ios/Runner/Base.lproj/Main.storyboard | 26 +
unionflow-mobile-apps/ios/Runner/Info.plist | 49 +
.../ios/Runner/Runner-Bridging-Header.h | 1 +
.../ios/RunnerTests/RunnerTests.swift | 12 +
unionflow-mobile-apps/lib/app.dart | 36 +
unionflow-mobile-apps/lib/app_temp.dart | 33 +
.../lib/app_ultra_simple.dart | 33 +
.../lib/core/auth/bloc/auth_bloc.dart | 203 +
.../lib/core/auth/bloc/auth_event.dart | 60 +
.../lib/core/auth/bloc/temp_auth_bloc.dart | 74 +
.../lib/core/auth/models/auth_state.dart | 140 +
.../lib/core/auth/models/login_request.dart | 50 +
.../lib/core/auth/models/login_response.dart | 96 +
.../lib/core/auth/models/models.dart | 5 +
.../lib/core/auth/models/user_info.dart | 90 +
.../core/auth/services/auth_api_service.dart | 306 +
.../lib/core/auth/services/auth_service.dart | 318 +
.../core/auth/services/temp_auth_service.dart | 70 +
.../services/ultra_simple_auth_service.dart | 86 +
.../auth/storage/memory_token_storage.dart | 117 +
.../auth/storage/secure_token_storage.dart | 246 +
.../lib/core/constants/app_constants.dart | 74 +
.../lib/core/di/injection.config.dart | 45 +
.../lib/core/di/injection.dart | 19 +
.../lib/core/errors/failures.dart | 122 +
.../lib/core/network/auth_interceptor.dart | 167 +
.../lib/core/network/dio_client.dart | 113 +
.../lib/core/utils/responsive_utils.dart | 111 +
.../auth/presentation/pages/auth_wrapper.dart | 69 +
.../pages/forgot_password_screen.dart | 489 ++
.../auth/presentation/pages/login_page.dart | 321 +
.../presentation/pages/login_page_temp.dart | 478 +
.../auth/presentation/pages/login_screen.dart | 517 ++
.../presentation/pages/register_screen.dart | 624 ++
.../presentation/pages/welcome_screen.dart | 400 +
.../presentation/widgets/login_footer.dart | 362 +
.../auth/presentation/widgets/login_form.dart | 437 +
.../presentation/widgets/login_header.dart | 259 +
.../presentation/pages/dashboard_page.dart | 675 ++
.../pages/enhanced_dashboard.dart | 485 ++
.../presentation/widgets/activity_feed.dart | 218 +
.../presentation/widgets/chart_card.dart | 335 +
.../widgets/clickable_kpi_card.dart | 252 +
.../presentation/widgets/kpi_card.dart | 116 +
.../widgets/navigation_cards.dart | 281 +
.../widgets/quick_actions_grid.dart | 214 +
.../presentation/pages/members_list_page.dart | 627 ++
.../presentation/widgets/member_card.dart | 427 +
.../widgets/members_filter_sheet.dart | 377 +
.../widgets/members_search_bar.dart | 133 +
.../widgets/sophisticated_member_card.dart | 544 ++
.../presentation/pages/main_navigation.dart | 406 +
.../widgets/custom_bottom_nav_bar.dart | 211 +
.../presentation/pages/splash_screen.dart | 306 +
unionflow-mobile-apps/lib/main.dart | 80 +
unionflow-mobile-apps/lib/main_temp.dart | 80 +
.../lib/main_ultra_simple.dart | 83 +
.../lib/shared/theme/app_theme.dart | 291 +
.../widgets/avatars/sophisticated_avatar.dart | 409 +
.../shared/widgets/badges/count_badge.dart | 202 +
.../shared/widgets/badges/status_badge.dart | 405 +
.../shared/widgets/buttons/button_group.dart | 383 +
.../lib/shared/widgets/buttons/buttons.dart | 303 +
.../buttons/floating_action_button.dart | 400 +
.../shared/widgets/buttons/icon_button.dart | 356 +
.../widgets/buttons/sophisticated_button.dart | 554 ++
.../widgets/cards/sophisticated_card.dart | 322 +
.../lib/shared/widgets/coming_soon_page.dart | 213 +
.../lib/shared/widgets/custom_text_field.dart | 248 +
.../lib/shared/widgets/loading_button.dart | 203 +
unionflow-mobile-apps/package.json | 96 +
unionflow-mobile-apps/pubspec.lock | 807 ++
unionflow-mobile-apps/pubspec.yaml | 43 +
unionflow-mobile-apps/pubspec_minimal.yaml | 27 +
unionflow-mobile-apps/pubspec_simple.yaml | 43 +
unionflow-mobile-apps/quick_start.ps1 | 43 +
unionflow-mobile-apps/src/App.tsx | 188 +
.../src/contexts/WavePaymentContext.tsx | 334 +
.../src/navigation/AppNavigator.tsx | 368 +
.../src/screens/payment/WavePaymentScreen.tsx | 600 ++
.../src/services/WavePaymentService.ts | 433 +
unionflow-mobile-apps/src/theme/theme.ts | 358 +
unionflow-mobile-apps/test/widget_test.dart | 22 +
unionflow-mobile-apps/test_minimal.ps1 | 30 +
unionflow-mobile-apps/test_temp.ps1 | 19 +
unionflow-server-api/pom.xml | 70 +
unionflow-server-impl-quarkus/pom.xml | 170 +
.../server/UnionFlowServerApplication.java | 35 +
.../server/resource/HealthResource.java | 35 +
.../src/main/resources/application.yml | 127 +
583 files changed, 243074 insertions(+)
create mode 100644 .gitignore
create mode 100644 pom.xml
create mode 100644 unionflow-client-quarkus-primefaces-freya/pom.xml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/UnionFlowClientApplication.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/converter/MembreConverter.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/dto/AssociationDTO.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/dto/FormulaireDTO.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/dto/MembreDTO.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/dto/SouscriptionDTO.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/dto/auth/LoginRequest.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/dto/auth/LoginResponse.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/exception/ViewExpiredExceptionHandler.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/exception/ViewExpiredExceptionHandlerFactory.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/security/AuthenticationFilter.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/security/JwtClientRequestFilter.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/security/JwtTokenManager.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/security/PermissionChecker.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/security/TokenCleanupService.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/security/TokenRefreshService.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/service/AssociationService.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/service/AuthenticationService.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/service/MembreService.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/service/RestClientExceptionMapper.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/service/ValidationService.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/validation/MemberNumberValidator.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/validation/PhoneNumberValidator.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/validation/ValidMemberNumber.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/validation/ValidPhoneNumber.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/validation/ValidationGroups.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/AdminFormulaireBean.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/AuditBean.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/ConfigurationBean.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/CotisationsBean.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/CotisationsGestionBean.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/DashboardBean.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/DemandesAideBean.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/DemandesBean.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/DocumentsBean.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/EntitesGestionBean.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/EvenementsBean.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/FormulaireBean.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/GuestPreferences.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/GuideBean.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/HelloView.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/LoginBean.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/MembreCotisationBean.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/MembreDashboardBean.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/MembreInscriptionBean.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/MembreListeBean.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/MembreProfilBean.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/MembreRechercheBean.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/NavigationBean.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/RapportsBean.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/RolesBean.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/SecurityStatusBean.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/SouscriptionBean.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/SuperAdminBean.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/UserSession.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/UtilisateursBean.java
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/faces-config.xml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/css/layout-dark.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/css/layout-dark.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/css/layout-light.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/css/layout-light.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/css/primeflex-v2.min.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/css/primeflex.min.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/css/primeicons.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/error/viewExpired.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/freya-layout/css/layout-dark.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/freya-layout/css/layout-dark.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/freya-layout/css/layout-light.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/freya-layout/css/layout-light.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/freya-layout/css/primeflex-v2.min.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/freya-layout/css/primeflex.min.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/freya-layout/css/primeicons.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/freya-layout/icons/primeicons.eot
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/freya-layout/icons/primeicons.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/freya-layout/icons/primeicons.ttf
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/freya-layout/icons/primeicons.woff
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/freya-layout/images/avatar-profilemenu.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/freya-layout/images/favicon.ico
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/freya-layout/images/logo-freya-single.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/freya-layout/images/logo-freya-white.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/freya-layout/images/logo-freya.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/freya-layout/images/pages/asset-404.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/freya-layout/images/pages/asset-access.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/freya-layout/images/pages/asset-error.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/freya-layout/images/pages/asset-landing-header.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/freya-layout/images/pages/search.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/freya-layout/js/layout.js
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/freya-layout/js/prism.js
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/icons/primeicons.eot
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/icons/primeicons.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/icons/primeicons.ttf
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/icons/primeicons.woff
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/images/avatar-profilemenu.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/images/favicon.ico
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/images/logo-freya-single.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/images/logo-freya-white.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/images/logo-freya.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/images/pages/asset-404.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/images/pages/asset-access.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/images/pages/asset-error.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/images/pages/asset-landing-header.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/images/pages/search.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/index.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/js/layout.js
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/js/prism.js
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/admin/aides/gestion.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/admin/audit.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/admin/audit/journal.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/admin/backup.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/admin/cotisations/gestion.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/admin/demandes/aide-sociale.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/admin/demandes/gestion-old.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/admin/demandes/gestion.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/admin/documents/gestion.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/admin/evenements/creation.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/admin/evenements/gestion.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/admin/evenements/liste.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/admin/evenements/participants.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/admin/finance/caisse.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/admin/rapports/finances.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/admin/rapports/statistiques.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/admin/settings.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/admin/users.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/admin/utilisateurs/gestion.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/membre/cotisations.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/membre/dashboard.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/public/formulaires.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/public/home.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/public/login.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/access-denied.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/adhesion/demande.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/adhesion/history.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/adhesion/liste.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/adhesion/new.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/adhesion/pending.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/adhesion/renouvellement.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/adhesion/validation.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/admin/audit.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/admin/parametres.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/admin/roles.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/admin/sauvegarde.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/admin/utilisateurs.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/aide/approved.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/aide/apropos.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/aide/demande.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/aide/documentation.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/aide/faq.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/aide/guide.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/aide/historique.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/aide/history.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/aide/nouveautes.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/aide/requests.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/aide/statistiques.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/aide/suggestions.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/aide/support.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/aide/tickets.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/aide/traitement.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/aide/tutoriels.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/cotisation/collect.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/cotisation/historique.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/cotisation/paiement.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/cotisation/rapports.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/cotisation/relances.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/cotisation/reminders.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/cotisation/report.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/dashboard.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/evenement/calendar.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/evenement/calendrier.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/evenement/create.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/evenement/creation.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/evenement/gestion.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/evenement/participants.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/evenement/participation.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/membre/inscription.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/membre/list.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/membre/liste.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/membre/new.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/membre/profil.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/membre/recherche.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/membre/search.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/personnel/activites.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/personnel/agenda.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/personnel/documents.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/personnel/favoris.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/personnel/notifications.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/personnel/parametres.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/personnel/preferences.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/personnel/profil.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/profile.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/rapport/activites.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/rapport/export.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/rapport/finances.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/rapport/membres.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/reports.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/souscription/dashboard.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/secure/stats.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/super-admin/configuration.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/super-admin/configuration/systeme.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/super-admin/dashboard-enhanced.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/super-admin/dashboard.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/super-admin/entites/gestion-enhanced.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/super-admin/entites/gestion.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/pages/super-admin/roles/gestion.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/primefaces-freya-avocado-dark/theme.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/primefaces-freya-avocado-dark/theme.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/primefaces-freya-avocado-light/theme.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/primefaces-freya-avocado-light/theme.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/primefaces-freya-blue-dark/theme.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/primefaces-freya-blue-dark/theme.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/primefaces-freya-blue-light/theme.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/primefaces-freya-blue-light/theme.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/primefaces-freya-green-dark/theme.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/primefaces-freya-green-dark/theme.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/primefaces-freya-green-light/theme.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/primefaces-freya-green-light/theme.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/primefaces-freya-orange-dark/theme.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/primefaces-freya-orange-dark/theme.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/primefaces-freya-orange-light/theme.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/primefaces-freya-orange-light/theme.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/primefaces-freya-purple-dark/theme.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/primefaces-freya-purple-dark/theme.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/primefaces-freya-purple-light/theme.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/primefaces-freya-purple-light/theme.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/primefaces-freya-red-dark/theme.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/primefaces-freya-red-dark/theme.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/primefaces-freya-red-light/theme.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/primefaces-freya-red-light/theme.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/primefaces-freya-turquoise-dark/theme.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/primefaces-freya-turquoise-dark/theme.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/primefaces-freya-turquoise-light/theme.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/primefaces-freya-turquoise-light/theme.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/primefaces-freya-yellow-dark/theme.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/primefaces-freya-yellow-dark/theme.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/primefaces-freya-yellow-light/theme.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/primefaces-freya-yellow-light/theme.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/chartjs/chart.js
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/css/_demo_common.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/css/demo-dark.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/css/demo-dark.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/css/demo-light.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/css/demo-light.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/css/flags/flags.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/css/flags/flags_responsive.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/css/pages/_blocks.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/css/pages/_chronoline.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/css/pages/_common.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/css/pages/_crud.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/css/pages/_documentation.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/css/pages/_floatlabel.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/css/pages/_icons.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/css/pages/_list.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/css/pages/_messages.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/css/pages/_misc.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/css/pages/_syntax.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/css/pages/_table.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/avatar/amyelsner.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/avatar/annafali.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/avatar/asiyajavayant.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/avatar/bernardodominic.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/avatar/elwinsharvill.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/avatar/ionibowcher.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/avatar/ivanmagalhaes.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/avatar/onyamalimba.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/avatar/profile.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/avatar/stephenshaw.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/avatar/xuxuefeng.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/blocks/hero/hero-1.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/blocks/logos/hyper.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/car/Audi.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/car/BMW.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/car/Fiat.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/car/Ford.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/car/Honda.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/car/Jaguar.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/car/Mercedes.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/car/Renault.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/car/Volkswagen.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/car/Volvo.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/dashboard/asset-image.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/dashboard/asset-map.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/dashboard/avatar/avatar-1.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/dashboard/avatar/avatar-2.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/dashboard/avatar/avatar-3.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/dashboard/avatar/avatar-4.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/dashboard/avatar/avatar-5.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/dashboard/avatar/avatar-6.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/dashboard/avatar/avatar-7.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/dashboard/mini-graph-1.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/dashboard/mini-graph-2.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/dashboard/mini-graph-3.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/dashboard/mini-graph-4.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/dashboard/mini-graph-5.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/dashboard/subtract.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/galleria/galleria1.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/galleria/galleria10.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/galleria/galleria10s.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/galleria/galleria11.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/galleria/galleria11s.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/galleria/galleria12.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/galleria/galleria12s.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/galleria/galleria13.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/galleria/galleria13s.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/galleria/galleria14.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/galleria/galleria14s.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/galleria/galleria15.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/galleria/galleria15s.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/galleria/galleria1s.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/galleria/galleria2.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/galleria/galleria2s.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/galleria/galleria3.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/galleria/galleria3s.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/galleria/galleria4.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/galleria/galleria4s.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/galleria/galleria5.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/galleria/galleria5s.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/galleria/galleria6.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/galleria/galleria6s.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/galleria/galleria7.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/galleria/galleria7s.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/galleria/galleria8.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/galleria/galleria8s.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/galleria/galleria9.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/galleria/galleria9s.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/nature/nature.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/product/bamboo-watch.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/product/black-watch.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/product/blue-band.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/product/blue-t-shirt.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/product/bracelet.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/product/brown-purse.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/product/chakra-bracelet.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/product/galaxy-earrings.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/product/game-controller.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/product/gaming-set.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/product/gold-phone-case.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/product/green-earbuds.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/product/green-t-shirt.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/product/grey-t-shirt.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/product/headphones.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/product/light-green-t-shirt.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/product/lime-band.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/product/mini-speakers.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/product/painted-phone-case.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/product/pink-band.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/product/pink-purse.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/product/purple-band.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/product/purple-gemstone-necklace.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/product/purple-t-shirt.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/product/shoes.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/product/sneakers.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/product/teal-t-shirt.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/product/yellow-earbuds.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/product/yoga-mat.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/product/yoga-set.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/rightpanel/asset-weather.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/rightpanel/aws.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/rightpanel/github.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/rightpanel/icon-sun.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/rightpanel/jenkins.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/rightpanel/jira.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/rightpanel/profile-1.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/rightpanel/profile-2.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/rightpanel/profile-3.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/rightpanel/profile-4.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/demo/images/rightpanel/slack.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/freya-layout/css/layout-dark.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/freya-layout/css/layout-dark.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/freya-layout/css/layout-light.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/freya-layout/css/layout-light.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/freya-layout/css/primeflex-v2.min.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/freya-layout/css/primeflex.min.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/freya-layout/css/primeicons.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/freya-layout/icons/primeicons.eot
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/freya-layout/icons/primeicons.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/freya-layout/icons/primeicons.ttf
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/freya-layout/icons/primeicons.woff
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/freya-layout/images/avatar-profilemenu.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/freya-layout/images/favicon.ico
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/freya-layout/images/logo-freya-single.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/freya-layout/images/logo-freya-white.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/freya-layout/images/logo-freya.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/freya-layout/images/pages/asset-404.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/freya-layout/images/pages/asset-access.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/freya-layout/images/pages/asset-error.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/freya-layout/images/pages/asset-landing-header.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/freya-layout/images/pages/search.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/freya-layout/js/layout.js
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/resources/freya-layout/js/prism.js
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/templates/components/config.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/templates/components/footer.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/templates/components/menu.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/templates/components/rightpanel.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/templates/components/topbar.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/templates/main-template.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/META-INF/resources/templates/public-template.xhtml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/ValidationMessages.properties
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/resources/application.properties
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/webapp/WEB-INF/beans.xml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/webapp/WEB-INF/faces-config.xml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/webapp/WEB-INF/primefaces-freya.taglib.xml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/webapp/WEB-INF/web.xml
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/webapp/resources/css/layout-dark.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/webapp/resources/css/layout-dark.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/webapp/resources/css/layout-light.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/webapp/resources/css/layout-light.scss
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/webapp/resources/css/primeflex-v2.min.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/webapp/resources/css/primeflex.min.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/webapp/resources/css/primeicons.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/webapp/resources/icons/primeicons.eot
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/webapp/resources/icons/primeicons.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/webapp/resources/icons/primeicons.ttf
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/webapp/resources/icons/primeicons.woff
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/webapp/resources/images/avatar-profilemenu.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/webapp/resources/images/favicon.ico
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/webapp/resources/images/logo-freya-single.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/webapp/resources/images/logo-freya-white.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/webapp/resources/images/logo-freya.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/webapp/resources/images/pages/asset-404.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/webapp/resources/images/pages/asset-access.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/webapp/resources/images/pages/asset-error.svg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/webapp/resources/images/pages/asset-landing-header.jpg
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/webapp/resources/images/pages/search.png
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/webapp/resources/js/layout.js
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/webapp/resources/js/prism.js
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/webapp/resources/primefaces-freya-blue-light/theme.css
create mode 100644 unionflow-client-quarkus-primefaces-freya/src/main/webapp/resources/primefaces-freya-blue-light/theme.scss
create mode 100644 unionflow-mobile-apps/.gitignore
create mode 100644 unionflow-mobile-apps/.metadata
create mode 100644 unionflow-mobile-apps/README.md
create mode 100644 unionflow-mobile-apps/README_DEMARRAGE.md
create mode 100644 unionflow-mobile-apps/analysis_options.yaml
create mode 100644 unionflow-mobile-apps/android/.gitignore
create mode 100644 unionflow-mobile-apps/android/app/build.gradle
create mode 100644 unionflow-mobile-apps/android/app/src/debug/AndroidManifest.xml
create mode 100644 unionflow-mobile-apps/android/app/src/main/AndroidManifest.xml
create mode 100644 unionflow-mobile-apps/android/app/src/main/kotlin/dev/lions/unionflow_mobile_apps/MainActivity.kt
create mode 100644 unionflow-mobile-apps/android/app/src/main/res/drawable-v21/launch_background.xml
create mode 100644 unionflow-mobile-apps/android/app/src/main/res/drawable/launch_background.xml
create mode 100644 unionflow-mobile-apps/android/app/src/main/res/mipmap-hdpi/ic_launcher.png
create mode 100644 unionflow-mobile-apps/android/app/src/main/res/mipmap-mdpi/ic_launcher.png
create mode 100644 unionflow-mobile-apps/android/app/src/main/res/mipmap-xhdpi/ic_launcher.png
create mode 100644 unionflow-mobile-apps/android/app/src/main/res/mipmap-xxhdpi/ic_launcher.png
create mode 100644 unionflow-mobile-apps/android/app/src/main/res/mipmap-xxxhdpi/ic_launcher.png
create mode 100644 unionflow-mobile-apps/android/app/src/main/res/values-night/styles.xml
create mode 100644 unionflow-mobile-apps/android/app/src/main/res/values/styles.xml
create mode 100644 unionflow-mobile-apps/android/app/src/profile/AndroidManifest.xml
create mode 100644 unionflow-mobile-apps/android/build.gradle
create mode 100644 unionflow-mobile-apps/android/gradle.properties
create mode 100644 unionflow-mobile-apps/android/gradle/wrapper/gradle-wrapper.properties
create mode 100644 unionflow-mobile-apps/android/settings.gradle
create mode 100644 unionflow-mobile-apps/fix-gradle-build.ps1
create mode 100644 unionflow-mobile-apps/fix-gradle-build.sh
create mode 100644 unionflow-mobile-apps/fix_and_run.ps1
create mode 100644 unionflow-mobile-apps/install_and_test.ps1
create mode 100644 unionflow-mobile-apps/install_and_test.sh
create mode 100644 unionflow-mobile-apps/ios/.gitignore
create mode 100644 unionflow-mobile-apps/ios/Flutter/AppFrameworkInfo.plist
create mode 100644 unionflow-mobile-apps/ios/Flutter/Debug.xcconfig
create mode 100644 unionflow-mobile-apps/ios/Flutter/Release.xcconfig
create mode 100644 unionflow-mobile-apps/ios/Runner.xcodeproj/project.pbxproj
create mode 100644 unionflow-mobile-apps/ios/Runner.xcodeproj/project.xcworkspace/contents.xcworkspacedata
create mode 100644 unionflow-mobile-apps/ios/Runner.xcodeproj/project.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist
create mode 100644 unionflow-mobile-apps/ios/Runner.xcodeproj/project.xcworkspace/xcshareddata/WorkspaceSettings.xcsettings
create mode 100644 unionflow-mobile-apps/ios/Runner.xcodeproj/xcshareddata/xcschemes/Runner.xcscheme
create mode 100644 unionflow-mobile-apps/ios/Runner.xcworkspace/contents.xcworkspacedata
create mode 100644 unionflow-mobile-apps/ios/Runner.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist
create mode 100644 unionflow-mobile-apps/ios/Runner.xcworkspace/xcshareddata/WorkspaceSettings.xcsettings
create mode 100644 unionflow-mobile-apps/ios/Runner/AppDelegate.swift
create mode 100644 unionflow-mobile-apps/ios/Runner/Assets.xcassets/AppIcon.appiconset/Contents.json
create mode 100644 unionflow-mobile-apps/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-1024x1024@1x.png
create mode 100644 unionflow-mobile-apps/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-20x20@1x.png
create mode 100644 unionflow-mobile-apps/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-20x20@2x.png
create mode 100644 unionflow-mobile-apps/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-20x20@3x.png
create mode 100644 unionflow-mobile-apps/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-29x29@1x.png
create mode 100644 unionflow-mobile-apps/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-29x29@2x.png
create mode 100644 unionflow-mobile-apps/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-29x29@3x.png
create mode 100644 unionflow-mobile-apps/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-40x40@1x.png
create mode 100644 unionflow-mobile-apps/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-40x40@2x.png
create mode 100644 unionflow-mobile-apps/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-40x40@3x.png
create mode 100644 unionflow-mobile-apps/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-60x60@2x.png
create mode 100644 unionflow-mobile-apps/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-60x60@3x.png
create mode 100644 unionflow-mobile-apps/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-76x76@1x.png
create mode 100644 unionflow-mobile-apps/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-76x76@2x.png
create mode 100644 unionflow-mobile-apps/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-83.5x83.5@2x.png
create mode 100644 unionflow-mobile-apps/ios/Runner/Assets.xcassets/LaunchImage.imageset/Contents.json
create mode 100644 unionflow-mobile-apps/ios/Runner/Assets.xcassets/LaunchImage.imageset/LaunchImage.png
create mode 100644 unionflow-mobile-apps/ios/Runner/Assets.xcassets/LaunchImage.imageset/LaunchImage@2x.png
create mode 100644 unionflow-mobile-apps/ios/Runner/Assets.xcassets/LaunchImage.imageset/LaunchImage@3x.png
create mode 100644 unionflow-mobile-apps/ios/Runner/Assets.xcassets/LaunchImage.imageset/README.md
create mode 100644 unionflow-mobile-apps/ios/Runner/Base.lproj/LaunchScreen.storyboard
create mode 100644 unionflow-mobile-apps/ios/Runner/Base.lproj/Main.storyboard
create mode 100644 unionflow-mobile-apps/ios/Runner/Info.plist
create mode 100644 unionflow-mobile-apps/ios/Runner/Runner-Bridging-Header.h
create mode 100644 unionflow-mobile-apps/ios/RunnerTests/RunnerTests.swift
create mode 100644 unionflow-mobile-apps/lib/app.dart
create mode 100644 unionflow-mobile-apps/lib/app_temp.dart
create mode 100644 unionflow-mobile-apps/lib/app_ultra_simple.dart
create mode 100644 unionflow-mobile-apps/lib/core/auth/bloc/auth_bloc.dart
create mode 100644 unionflow-mobile-apps/lib/core/auth/bloc/auth_event.dart
create mode 100644 unionflow-mobile-apps/lib/core/auth/bloc/temp_auth_bloc.dart
create mode 100644 unionflow-mobile-apps/lib/core/auth/models/auth_state.dart
create mode 100644 unionflow-mobile-apps/lib/core/auth/models/login_request.dart
create mode 100644 unionflow-mobile-apps/lib/core/auth/models/login_response.dart
create mode 100644 unionflow-mobile-apps/lib/core/auth/models/models.dart
create mode 100644 unionflow-mobile-apps/lib/core/auth/models/user_info.dart
create mode 100644 unionflow-mobile-apps/lib/core/auth/services/auth_api_service.dart
create mode 100644 unionflow-mobile-apps/lib/core/auth/services/auth_service.dart
create mode 100644 unionflow-mobile-apps/lib/core/auth/services/temp_auth_service.dart
create mode 100644 unionflow-mobile-apps/lib/core/auth/services/ultra_simple_auth_service.dart
create mode 100644 unionflow-mobile-apps/lib/core/auth/storage/memory_token_storage.dart
create mode 100644 unionflow-mobile-apps/lib/core/auth/storage/secure_token_storage.dart
create mode 100644 unionflow-mobile-apps/lib/core/constants/app_constants.dart
create mode 100644 unionflow-mobile-apps/lib/core/di/injection.config.dart
create mode 100644 unionflow-mobile-apps/lib/core/di/injection.dart
create mode 100644 unionflow-mobile-apps/lib/core/errors/failures.dart
create mode 100644 unionflow-mobile-apps/lib/core/network/auth_interceptor.dart
create mode 100644 unionflow-mobile-apps/lib/core/network/dio_client.dart
create mode 100644 unionflow-mobile-apps/lib/core/utils/responsive_utils.dart
create mode 100644 unionflow-mobile-apps/lib/features/auth/presentation/pages/auth_wrapper.dart
create mode 100644 unionflow-mobile-apps/lib/features/auth/presentation/pages/forgot_password_screen.dart
create mode 100644 unionflow-mobile-apps/lib/features/auth/presentation/pages/login_page.dart
create mode 100644 unionflow-mobile-apps/lib/features/auth/presentation/pages/login_page_temp.dart
create mode 100644 unionflow-mobile-apps/lib/features/auth/presentation/pages/login_screen.dart
create mode 100644 unionflow-mobile-apps/lib/features/auth/presentation/pages/register_screen.dart
create mode 100644 unionflow-mobile-apps/lib/features/auth/presentation/pages/welcome_screen.dart
create mode 100644 unionflow-mobile-apps/lib/features/auth/presentation/widgets/login_footer.dart
create mode 100644 unionflow-mobile-apps/lib/features/auth/presentation/widgets/login_form.dart
create mode 100644 unionflow-mobile-apps/lib/features/auth/presentation/widgets/login_header.dart
create mode 100644 unionflow-mobile-apps/lib/features/dashboard/presentation/pages/dashboard_page.dart
create mode 100644 unionflow-mobile-apps/lib/features/dashboard/presentation/pages/enhanced_dashboard.dart
create mode 100644 unionflow-mobile-apps/lib/features/dashboard/presentation/widgets/activity_feed.dart
create mode 100644 unionflow-mobile-apps/lib/features/dashboard/presentation/widgets/chart_card.dart
create mode 100644 unionflow-mobile-apps/lib/features/dashboard/presentation/widgets/clickable_kpi_card.dart
create mode 100644 unionflow-mobile-apps/lib/features/dashboard/presentation/widgets/kpi_card.dart
create mode 100644 unionflow-mobile-apps/lib/features/dashboard/presentation/widgets/navigation_cards.dart
create mode 100644 unionflow-mobile-apps/lib/features/dashboard/presentation/widgets/quick_actions_grid.dart
create mode 100644 unionflow-mobile-apps/lib/features/members/presentation/pages/members_list_page.dart
create mode 100644 unionflow-mobile-apps/lib/features/members/presentation/widgets/member_card.dart
create mode 100644 unionflow-mobile-apps/lib/features/members/presentation/widgets/members_filter_sheet.dart
create mode 100644 unionflow-mobile-apps/lib/features/members/presentation/widgets/members_search_bar.dart
create mode 100644 unionflow-mobile-apps/lib/features/members/presentation/widgets/sophisticated_member_card.dart
create mode 100644 unionflow-mobile-apps/lib/features/navigation/presentation/pages/main_navigation.dart
create mode 100644 unionflow-mobile-apps/lib/features/navigation/presentation/widgets/custom_bottom_nav_bar.dart
create mode 100644 unionflow-mobile-apps/lib/features/splash/presentation/pages/splash_screen.dart
create mode 100644 unionflow-mobile-apps/lib/main.dart
create mode 100644 unionflow-mobile-apps/lib/main_temp.dart
create mode 100644 unionflow-mobile-apps/lib/main_ultra_simple.dart
create mode 100644 unionflow-mobile-apps/lib/shared/theme/app_theme.dart
create mode 100644 unionflow-mobile-apps/lib/shared/widgets/avatars/sophisticated_avatar.dart
create mode 100644 unionflow-mobile-apps/lib/shared/widgets/badges/count_badge.dart
create mode 100644 unionflow-mobile-apps/lib/shared/widgets/badges/status_badge.dart
create mode 100644 unionflow-mobile-apps/lib/shared/widgets/buttons/button_group.dart
create mode 100644 unionflow-mobile-apps/lib/shared/widgets/buttons/buttons.dart
create mode 100644 unionflow-mobile-apps/lib/shared/widgets/buttons/floating_action_button.dart
create mode 100644 unionflow-mobile-apps/lib/shared/widgets/buttons/icon_button.dart
create mode 100644 unionflow-mobile-apps/lib/shared/widgets/buttons/sophisticated_button.dart
create mode 100644 unionflow-mobile-apps/lib/shared/widgets/cards/sophisticated_card.dart
create mode 100644 unionflow-mobile-apps/lib/shared/widgets/coming_soon_page.dart
create mode 100644 unionflow-mobile-apps/lib/shared/widgets/custom_text_field.dart
create mode 100644 unionflow-mobile-apps/lib/shared/widgets/loading_button.dart
create mode 100644 unionflow-mobile-apps/package.json
create mode 100644 unionflow-mobile-apps/pubspec.lock
create mode 100644 unionflow-mobile-apps/pubspec.yaml
create mode 100644 unionflow-mobile-apps/pubspec_minimal.yaml
create mode 100644 unionflow-mobile-apps/pubspec_simple.yaml
create mode 100644 unionflow-mobile-apps/quick_start.ps1
create mode 100644 unionflow-mobile-apps/src/App.tsx
create mode 100644 unionflow-mobile-apps/src/contexts/WavePaymentContext.tsx
create mode 100644 unionflow-mobile-apps/src/navigation/AppNavigator.tsx
create mode 100644 unionflow-mobile-apps/src/screens/payment/WavePaymentScreen.tsx
create mode 100644 unionflow-mobile-apps/src/services/WavePaymentService.ts
create mode 100644 unionflow-mobile-apps/src/theme/theme.ts
create mode 100644 unionflow-mobile-apps/test/widget_test.dart
create mode 100644 unionflow-mobile-apps/test_minimal.ps1
create mode 100644 unionflow-mobile-apps/test_temp.ps1
create mode 100644 unionflow-server-api/pom.xml
create mode 100644 unionflow-server-impl-quarkus/pom.xml
create mode 100644 unionflow-server-impl-quarkus/src/main/java/dev/lions/unionflow/server/UnionFlowServerApplication.java
create mode 100644 unionflow-server-impl-quarkus/src/main/java/dev/lions/unionflow/server/resource/HealthResource.java
create mode 100644 unionflow-server-impl-quarkus/src/main/resources/application.yml
diff --git a/.gitignore b/.gitignore
new file mode 100644
index 0000000..137cee6
--- /dev/null
+++ b/.gitignore
@@ -0,0 +1,30 @@
+# Build
+target/
+**/target/
+.mvn/wrapper/maven-wrapper.jar
+
+# IDE
+.idea/
+.vscode/
+*.iml
+*.ipr
+*.iws
+
+# OS
+.DS_Store
+Thumbs.db
+
+# Logs
+logs/
+*.log
+
+# Environment
+.env
+.env.local
+
+# Quarkus
+.quarkus/
+
+.claude/
+.dockerignore
+.env.example
diff --git a/pom.xml b/pom.xml
new file mode 100644
index 0000000..1abbed5
--- /dev/null
+++ b/pom.xml
@@ -0,0 +1,42 @@
+
+
+ 4.0.0
+
+ dev.lions.unionflow
+ unionflow-parent
+ 1.0.0
+ pom
+
+ UnionFlow - Gestion d'Union
+ Plateforme complète de gestion d'union avec mobile et web
+
+
+ 17
+ 17
+ UTF-8
+ 3.15.1
+
+
+
+ unionflow-server-api
+ unionflow-server-impl-quarkus
+ unionflow-client-quarkus-primefaces-freya
+
+
+
+
+
+ org.apache.maven.plugins
+ maven-compiler-plugin
+ 3.11.0
+
+ 17
+ 17
+ UTF-8
+
+
+
+
+
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/pom.xml b/unionflow-client-quarkus-primefaces-freya/pom.xml
new file mode 100644
index 0000000..0c37329
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/pom.xml
@@ -0,0 +1,210 @@
+
+
+ 4.0.0
+
+ dev.lions.unionflow
+ unionflow-client-quarkus-primefaces-freya
+ 1.0.0
+ jar
+
+ UnionFlow Client (Quarkus + PrimeFaces Freya)
+ Client web UnionFlow avec Quarkus et PrimeFaces Freya
+
+
+ 17
+ 17
+ UTF-8
+ UTF-8
+
+ 3.15.1
+ io.quarkus.platform
+ quarkus-bom
+ 3.13.3
+ 14.0.5
+ 4.4.1
+
+
+
+
+
+ ${quarkus.platform.group-id}
+ ${quarkus.platform.artifact-id}
+ ${quarkus.platform.version}
+ pom
+ import
+
+
+
+
+
+
+
+ io.quarkus
+ quarkus-arc
+
+
+
+
+ io.quarkiverse.primefaces
+ quarkus-primefaces
+ ${quarkus-primefaces.version}
+
+
+
+
+ io.quarkiverse.omnifaces
+ quarkus-omnifaces
+ 4.4.1
+
+
+
+
+ org.primefaces.themes
+ freya-theme-jakarta
+ 5.0.0
+
+
+
+
+ io.quarkus
+ quarkus-undertow
+
+
+
+
+ io.quarkus
+ quarkus-rest-client
+
+
+ io.quarkus
+ quarkus-rest-client-jackson
+
+
+
+
+ io.quarkus
+ quarkus-smallrye-jwt
+
+
+
+
+ io.quarkus
+ quarkus-config-yaml
+
+
+
+
+ io.quarkus
+ quarkus-hibernate-validator
+
+
+
+
+ io.quarkus
+ quarkus-scheduler
+
+
+
+
+ org.apache.poi
+ poi
+ 5.2.5
+
+
+ org.apache.poi
+ poi-ooxml
+ 5.2.5
+
+
+ org.apache.xmlgraphics
+ batik-all
+
+
+
+
+ com.github.librepdf
+ openpdf
+ 1.3.30
+
+
+
+
+ io.quarkus
+ quarkus-junit5
+ test
+
+
+ io.rest-assured
+ rest-assured
+ test
+
+
+
+
+
+ prime-repo
+ PrimeFaces Maven Repository
+ https://repository.primefaces.org
+ default
+
+
+
+
+
+
+ ${quarkus.platform.group-id}
+ quarkus-maven-plugin
+ ${quarkus.platform.version}
+ true
+
+
+
+ build
+ generate-code
+ generate-code-tests
+
+
+
+
+
+ org.apache.maven.plugins
+ maven-compiler-plugin
+ 3.11.0
+
+ 17
+ 17
+ UTF-8
+ true
+
+
+
+ org.apache.maven.plugins
+ maven-surefire-plugin
+ 3.0.0
+
+
+ org.jboss.logmanager.LogManager
+ ${maven.home}
+
+
+
+
+
+
+
+
+ native
+
+
+ native
+
+
+
+ false
+ native
+
+
+
+
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/UnionFlowClientApplication.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/UnionFlowClientApplication.java
new file mode 100644
index 0000000..7e0a7a5
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/UnionFlowClientApplication.java
@@ -0,0 +1,34 @@
+package dev.lions.unionflow.client;
+
+import io.quarkus.runtime.Quarkus;
+import io.quarkus.runtime.QuarkusApplication;
+import io.quarkus.runtime.annotations.QuarkusMain;
+import jakarta.enterprise.context.ApplicationScoped;
+import org.jboss.logging.Logger;
+
+/**
+ * Application principale UnionFlow Client
+ *
+ * @author Lions Dev Team
+ * @version 1.0.0
+ */
+@QuarkusMain
+@ApplicationScoped
+public class UnionFlowClientApplication implements QuarkusApplication {
+
+ private static final Logger LOG = Logger.getLogger(UnionFlowClientApplication.class);
+
+ public static void main(String... args) {
+ Quarkus.run(UnionFlowClientApplication.class, args);
+ }
+
+ @Override
+ public int run(String... args) throws Exception {
+ LOG.info("UnionFlow Client démarré avec succès!");
+ LOG.info("Interface web disponible sur http://localhost:8082");
+ LOG.info("Page d'accueil sur http://localhost:8082/index.xhtml");
+
+ Quarkus.waitForExit();
+ return 0;
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/converter/MembreConverter.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/converter/MembreConverter.java
new file mode 100644
index 0000000..62d72b7
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/converter/MembreConverter.java
@@ -0,0 +1,43 @@
+package dev.lions.unionflow.client.converter;
+
+import jakarta.enterprise.context.ApplicationScoped;
+import jakarta.faces.component.UIComponent;
+import jakarta.faces.context.FacesContext;
+import jakarta.faces.convert.Converter;
+import jakarta.faces.convert.FacesConverter;
+import jakarta.inject.Named;
+import dev.lions.unionflow.client.view.DemandesBean.Membre;
+
+@Named
+@ApplicationScoped
+@FacesConverter(value = "membreConverter", managed = true)
+public class MembreConverter implements Converter {
+
+ @Override
+ public Membre getAsObject(FacesContext context, UIComponent component, String value) {
+ if (value == null || value.trim().isEmpty()) {
+ return null;
+ }
+
+ try {
+ // Parse the membre ID from the string value
+ Long membreId = Long.valueOf(value);
+
+ // Create a simple Membre object with just the ID
+ // In a real implementation, you would fetch from database
+ Membre membre = new Membre();
+ membre.setId(membreId);
+ return membre;
+ } catch (NumberFormatException e) {
+ return null;
+ }
+ }
+
+ @Override
+ public String getAsString(FacesContext context, UIComponent component, Membre value) {
+ if (value == null || value.getId() == null) {
+ return "";
+ }
+ return value.getId().toString();
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/dto/AssociationDTO.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/dto/AssociationDTO.java
new file mode 100644
index 0000000..4b33b1d
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/dto/AssociationDTO.java
@@ -0,0 +1,177 @@
+package dev.lions.unionflow.client.dto;
+
+import com.fasterxml.jackson.annotation.JsonFormat;
+import jakarta.validation.constraints.NotBlank;
+import jakarta.validation.constraints.NotNull;
+import java.time.LocalDate;
+import java.time.LocalDateTime;
+import java.io.Serializable;
+
+public class AssociationDTO implements Serializable {
+
+ private static final long serialVersionUID = 1L;
+
+ private Long id;
+
+ @NotBlank(message = "Le nom de l'association est obligatoire")
+ private String nom;
+
+ private String description;
+ private String adresse;
+ private String telephone;
+ private String email;
+ private String siteWeb;
+
+ @NotNull(message = "Le type d'association est obligatoire")
+ private String typeAssociation;
+
+ @JsonFormat(pattern = "yyyy-MM-dd")
+ private LocalDate dateCreation;
+
+ private String numeroRegistre;
+ private String statut;
+ private Integer nombreMembres;
+ private String responsablePrincipal;
+ private String telephoneResponsable;
+ private String emailResponsable;
+
+ @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss")
+ private LocalDateTime dateDerniereActivite;
+
+ private String region;
+ private String ville;
+ private String quartier;
+
+ // Constructeurs
+ public AssociationDTO() {}
+
+ public AssociationDTO(String nom, String typeAssociation) {
+ this.nom = nom;
+ this.typeAssociation = typeAssociation;
+ this.statut = "ACTIVE";
+ this.dateCreation = LocalDate.now();
+ this.nombreMembres = 0;
+ }
+
+ // Getters et Setters
+ public Long getId() { return id; }
+ public void setId(Long id) { this.id = id; }
+
+ public String getNom() { return nom; }
+ public void setNom(String nom) { this.nom = nom; }
+
+ public String getDescription() { return description; }
+ public void setDescription(String description) { this.description = description; }
+
+ public String getAdresse() { return adresse; }
+ public void setAdresse(String adresse) { this.adresse = adresse; }
+
+ public String getTelephone() { return telephone; }
+ public void setTelephone(String telephone) { this.telephone = telephone; }
+
+ public String getEmail() { return email; }
+ public void setEmail(String email) { this.email = email; }
+
+ public String getSiteWeb() { return siteWeb; }
+ public void setSiteWeb(String siteWeb) { this.siteWeb = siteWeb; }
+
+ public String getTypeAssociation() { return typeAssociation; }
+ public void setTypeAssociation(String typeAssociation) { this.typeAssociation = typeAssociation; }
+
+ public LocalDate getDateCreation() { return dateCreation; }
+ public void setDateCreation(LocalDate dateCreation) { this.dateCreation = dateCreation; }
+
+ public String getNumeroRegistre() { return numeroRegistre; }
+ public void setNumeroRegistre(String numeroRegistre) { this.numeroRegistre = numeroRegistre; }
+
+ public String getStatut() { return statut; }
+ public void setStatut(String statut) { this.statut = statut; }
+
+ public Integer getNombreMembres() { return nombreMembres; }
+ public void setNombreMembres(Integer nombreMembres) { this.nombreMembres = nombreMembres; }
+
+ public String getResponsablePrincipal() { return responsablePrincipal; }
+ public void setResponsablePrincipal(String responsablePrincipal) { this.responsablePrincipal = responsablePrincipal; }
+
+ public String getTelephoneResponsable() { return telephoneResponsable; }
+ public void setTelephoneResponsable(String telephoneResponsable) { this.telephoneResponsable = telephoneResponsable; }
+
+ public String getEmailResponsable() { return emailResponsable; }
+ public void setEmailResponsable(String emailResponsable) { this.emailResponsable = emailResponsable; }
+
+ public LocalDateTime getDateDerniereActivite() { return dateDerniereActivite; }
+ public void setDateDerniereActivite(LocalDateTime dateDerniereActivite) { this.dateDerniereActivite = dateDerniereActivite; }
+
+ public String getRegion() { return region; }
+ public void setRegion(String region) { this.region = region; }
+
+ public String getVille() { return ville; }
+ public void setVille(String ville) { this.ville = ville; }
+
+ public String getQuartier() { return quartier; }
+ public void setQuartier(String quartier) { this.quartier = quartier; }
+
+ // Propriétés dérivées
+ public String getTypeLibelle() {
+ return switch (typeAssociation != null ? typeAssociation : "") {
+ case "LIONS_CLUB" -> "Club Lions";
+ case "ASSOCIATION_LOCALE" -> "Association Locale";
+ case "FEDERATION" -> "Fédération";
+ case "COOPERATIVE" -> "Coopérative";
+ case "MUTUELLE" -> "Mutuelle";
+ case "SYNDICAT" -> "Syndicat";
+ default -> typeAssociation;
+ };
+ }
+
+ public String getStatutLibelle() {
+ return switch (statut != null ? statut : "") {
+ case "ACTIVE" -> "Active";
+ case "INACTIVE" -> "Inactive";
+ case "SUSPENDUE" -> "Suspendue";
+ case "DISSOUTE" -> "Dissoute";
+ default -> statut;
+ };
+ }
+
+ public String getStatutSeverity() {
+ return switch (statut != null ? statut : "") {
+ case "ACTIVE" -> "success";
+ case "INACTIVE" -> "warning";
+ case "SUSPENDUE" -> "danger";
+ case "DISSOUTE" -> "secondary";
+ default -> "info";
+ };
+ }
+
+ public String getAdresseComplete() {
+ StringBuilder addr = new StringBuilder();
+ if (adresse != null && !adresse.trim().isEmpty()) {
+ addr.append(adresse);
+ }
+ if (quartier != null && !quartier.trim().isEmpty()) {
+ if (addr.length() > 0) addr.append(", ");
+ addr.append(quartier);
+ }
+ if (ville != null && !ville.trim().isEmpty()) {
+ if (addr.length() > 0) addr.append(", ");
+ addr.append(ville);
+ }
+ if (region != null && !region.trim().isEmpty()) {
+ if (addr.length() > 0) addr.append(", ");
+ addr.append(region);
+ }
+ return addr.toString();
+ }
+
+ @Override
+ public String toString() {
+ return "AssociationDTO{" +
+ "id=" + id +
+ ", nom='" + nom + '\'' +
+ ", typeAssociation='" + typeAssociation + '\'' +
+ ", statut='" + statut + '\'' +
+ ", nombreMembres=" + nombreMembres +
+ '}';
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/dto/FormulaireDTO.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/dto/FormulaireDTO.java
new file mode 100644
index 0000000..38f8408
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/dto/FormulaireDTO.java
@@ -0,0 +1,180 @@
+package dev.lions.unionflow.client.dto;
+
+import jakarta.validation.constraints.NotNull;
+import jakarta.validation.constraints.Positive;
+import java.io.Serializable;
+import java.math.BigDecimal;
+import java.time.LocalDateTime;
+
+public class FormulaireDTO implements Serializable {
+
+ private static final long serialVersionUID = 1L;
+
+ private Long id;
+
+ @NotNull
+ private String nom;
+
+ private String description;
+
+ @NotNull
+ @Positive
+ private Integer quotaMaxMembres;
+
+ @NotNull
+ private BigDecimal prixMensuel;
+
+ @NotNull
+ private BigDecimal prixAnnuel;
+
+ private String deviseCode = "XOF"; // Franc CFA
+
+ private boolean actif = true;
+
+ private boolean recommande = false;
+
+ private String couleurTheme;
+
+ private String iconeFormulaire;
+
+ // Fonctionnalités incluses
+ private boolean gestionMembres = true;
+ private boolean gestionCotisations = true;
+ private boolean gestionEvenements = false;
+ private boolean gestionAides = false;
+ private boolean rapportsAvances = false;
+ private boolean supportPrioritaire = false;
+ private boolean sauvegardeAutomatique = false;
+ private boolean personnalisationAvancee = false;
+ private boolean integrationPaiement = false;
+ private boolean notificationsEmail = false;
+ private boolean notificationsSMS = false;
+ private boolean gestionDocuments = false;
+
+ // Métadonnées
+ private LocalDateTime dateCreation;
+ private LocalDateTime dateMiseAJour;
+ private String creePar;
+ private String modifiePar;
+
+ public FormulaireDTO() {}
+
+ // Getters et Setters
+ public Long getId() { return id; }
+ public void setId(Long id) { this.id = id; }
+
+ public String getNom() { return nom; }
+ public void setNom(String nom) { this.nom = nom; }
+
+ public String getDescription() { return description; }
+ public void setDescription(String description) { this.description = description; }
+
+ public Integer getQuotaMaxMembres() { return quotaMaxMembres; }
+ public void setQuotaMaxMembres(Integer quotaMaxMembres) { this.quotaMaxMembres = quotaMaxMembres; }
+
+ public BigDecimal getPrixMensuel() { return prixMensuel; }
+ public void setPrixMensuel(BigDecimal prixMensuel) { this.prixMensuel = prixMensuel; }
+
+ public BigDecimal getPrixAnnuel() { return prixAnnuel; }
+ public void setPrixAnnuel(BigDecimal prixAnnuel) { this.prixAnnuel = prixAnnuel; }
+
+ public String getDeviseCode() { return deviseCode; }
+ public void setDeviseCode(String deviseCode) { this.deviseCode = deviseCode; }
+
+ public boolean isActif() { return actif; }
+ public void setActif(boolean actif) { this.actif = actif; }
+
+ public boolean isRecommande() { return recommande; }
+ public void setRecommande(boolean recommande) { this.recommande = recommande; }
+
+ public String getCouleurTheme() { return couleurTheme; }
+ public void setCouleurTheme(String couleurTheme) { this.couleurTheme = couleurTheme; }
+
+ public String getIconeFormulaire() { return iconeFormulaire; }
+ public void setIconeFormulaire(String iconeFormulaire) { this.iconeFormulaire = iconeFormulaire; }
+
+ // Fonctionnalités
+ public boolean isGestionMembres() { return gestionMembres; }
+ public void setGestionMembres(boolean gestionMembres) { this.gestionMembres = gestionMembres; }
+
+ public boolean isGestionCotisations() { return gestionCotisations; }
+ public void setGestionCotisations(boolean gestionCotisations) { this.gestionCotisations = gestionCotisations; }
+
+ public boolean isGestionEvenements() { return gestionEvenements; }
+ public void setGestionEvenements(boolean gestionEvenements) { this.gestionEvenements = gestionEvenements; }
+
+ public boolean isGestionAides() { return gestionAides; }
+ public void setGestionAides(boolean gestionAides) { this.gestionAides = gestionAides; }
+
+ public boolean isRapportsAvances() { return rapportsAvances; }
+ public void setRapportsAvances(boolean rapportsAvances) { this.rapportsAvances = rapportsAvances; }
+
+ public boolean isSupportPrioritaire() { return supportPrioritaire; }
+ public void setSupportPrioritaire(boolean supportPrioritaire) { this.supportPrioritaire = supportPrioritaire; }
+
+ public boolean isSauvegardeAutomatique() { return sauvegardeAutomatique; }
+ public void setSauvegardeAutomatique(boolean sauvegardeAutomatique) { this.sauvegardeAutomatique = sauvegardeAutomatique; }
+
+ public boolean isPersonnalisationAvancee() { return personnalisationAvancee; }
+ public void setPersonnalisationAvancee(boolean personnalisationAvancee) { this.personnalisationAvancee = personnalisationAvancee; }
+
+ public boolean isIntegrationPaiement() { return integrationPaiement; }
+ public void setIntegrationPaiement(boolean integrationPaiement) { this.integrationPaiement = integrationPaiement; }
+
+ public boolean isNotificationsEmail() { return notificationsEmail; }
+ public void setNotificationsEmail(boolean notificationsEmail) { this.notificationsEmail = notificationsEmail; }
+
+ public boolean isNotificationsSMS() { return notificationsSMS; }
+ public void setNotificationsSMS(boolean notificationsSMS) { this.notificationsSMS = notificationsSMS; }
+
+ public boolean isGestionDocuments() { return gestionDocuments; }
+ public void setGestionDocuments(boolean gestionDocuments) { this.gestionDocuments = gestionDocuments; }
+
+ // Métadonnées
+ public LocalDateTime getDateCreation() { return dateCreation; }
+ public void setDateCreation(LocalDateTime dateCreation) { this.dateCreation = dateCreation; }
+
+ public LocalDateTime getDateMiseAJour() { return dateMiseAJour; }
+ public void setDateMiseAJour(LocalDateTime dateMiseAJour) { this.dateMiseAJour = dateMiseAJour; }
+
+ public String getCreePar() { return creePar; }
+ public void setCreePar(String creePar) { this.creePar = creePar; }
+
+ public String getModifiePar() { return modifiePar; }
+ public void setModifiePar(String modifiePar) { this.modifiePar = modifiePar; }
+
+ // Méthodes utilitaires
+ public String getPrixMensuelFormat() {
+ return String.format("%,.0f %s", prixMensuel, deviseCode);
+ }
+
+ public String getPrixAnnuelFormat() {
+ return String.format("%,.0f %s", prixAnnuel, deviseCode);
+ }
+
+ public BigDecimal getEconomieAnnuelle() {
+ if (prixMensuel != null && prixAnnuel != null) {
+ BigDecimal coutMensuelAnnuel = prixMensuel.multiply(BigDecimal.valueOf(12));
+ return coutMensuelAnnuel.subtract(prixAnnuel);
+ }
+ return BigDecimal.ZERO;
+ }
+
+ public String getEconomieAnnuelleFormat() {
+ BigDecimal economie = getEconomieAnnuelle();
+ return String.format("%,.0f %s", economie, deviseCode);
+ }
+
+ public int getPourcentageEconomie() {
+ if (prixMensuel != null && prixAnnuel != null) {
+ BigDecimal coutMensuelAnnuel = prixMensuel.multiply(BigDecimal.valueOf(12));
+ BigDecimal economie = getEconomieAnnuelle();
+ if (coutMensuelAnnuel.compareTo(BigDecimal.ZERO) > 0) {
+ return economie.multiply(BigDecimal.valueOf(100))
+ .divide(coutMensuelAnnuel, 0, BigDecimal.ROUND_HALF_UP)
+ .intValue();
+ }
+ }
+ return 0;
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/dto/MembreDTO.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/dto/MembreDTO.java
new file mode 100644
index 0000000..137aaed
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/dto/MembreDTO.java
@@ -0,0 +1,187 @@
+package dev.lions.unionflow.client.dto;
+
+import dev.lions.unionflow.client.validation.ValidPhoneNumber;
+import dev.lions.unionflow.client.validation.ValidMemberNumber;
+import dev.lions.unionflow.client.validation.ValidationGroups;
+import com.fasterxml.jackson.annotation.JsonFormat;
+import jakarta.validation.constraints.*;
+import java.time.LocalDate;
+import java.time.LocalDateTime;
+import java.io.Serializable;
+
+public class MembreDTO implements Serializable {
+
+ private static final long serialVersionUID = 1L;
+
+ private Long id;
+
+ @NotBlank(message = "Le numéro de membre est obligatoire", groups = {ValidationGroups.CreateMember.class, ValidationGroups.FullRegistration.class})
+ @ValidMemberNumber(groups = {ValidationGroups.CreateMember.class, ValidationGroups.UpdateMember.class, ValidationGroups.FullRegistration.class})
+ private String numeroMembre;
+
+ @NotBlank(message = "Le nom est obligatoire", groups = {ValidationGroups.CreateMember.class, ValidationGroups.QuickRegistration.class, ValidationGroups.FullRegistration.class})
+ @Size(min = 2, max = 50, message = "Le nom doit contenir entre 2 et 50 caractères", groups = {ValidationGroups.CreateMember.class, ValidationGroups.UpdateMember.class, ValidationGroups.QuickRegistration.class, ValidationGroups.FullRegistration.class})
+ @Pattern(regexp = "^[a-zA-ZÀ-ÿ\\s\\-']+$", message = "Le nom ne peut contenir que des lettres, espaces, tirets et apostrophes", groups = {ValidationGroups.CreateMember.class, ValidationGroups.UpdateMember.class, ValidationGroups.QuickRegistration.class, ValidationGroups.FullRegistration.class})
+ private String nom;
+
+ @NotBlank(message = "Le prénom est obligatoire", groups = {ValidationGroups.CreateMember.class, ValidationGroups.QuickRegistration.class, ValidationGroups.FullRegistration.class})
+ @Size(min = 2, max = 50, message = "Le prénom doit contenir entre 2 et 50 caractères", groups = {ValidationGroups.CreateMember.class, ValidationGroups.UpdateMember.class, ValidationGroups.QuickRegistration.class, ValidationGroups.FullRegistration.class})
+ @Pattern(regexp = "^[a-zA-ZÀ-ÿ\\s\\-']+$", message = "Le prénom ne peut contenir que des lettres, espaces, tirets et apostrophes", groups = {ValidationGroups.CreateMember.class, ValidationGroups.UpdateMember.class, ValidationGroups.QuickRegistration.class, ValidationGroups.FullRegistration.class})
+ private String prenom;
+
+ @Email(message = "Format d'email invalide", groups = {ValidationGroups.CreateMember.class, ValidationGroups.UpdateMember.class, ValidationGroups.QuickRegistration.class, ValidationGroups.FullRegistration.class})
+ @Size(max = 100, message = "L'email ne peut pas dépasser 100 caractères", groups = {ValidationGroups.CreateMember.class, ValidationGroups.UpdateMember.class, ValidationGroups.QuickRegistration.class, ValidationGroups.FullRegistration.class})
+ private String email;
+
+ @ValidPhoneNumber
+ private String telephone;
+
+ @JsonFormat(pattern = "yyyy-MM-dd")
+ @Past(message = "La date de naissance doit être dans le passé")
+ private LocalDate dateNaissance;
+
+ @Size(max = 200, message = "L'adresse ne peut pas dépasser 200 caractères")
+ private String adresse;
+
+ @Size(max = 100, message = "La profession ne peut pas dépasser 100 caractères")
+ private String profession;
+
+ @Size(max = 20, message = "Le statut matrimonial ne peut pas dépasser 20 caractères")
+ private String statutMatrimonial;
+
+ @Size(max = 50, message = "La nationalité ne peut pas dépasser 50 caractères")
+ private String nationalite;
+
+ @Size(max = 50, message = "Le numéro d'identité ne peut pas dépasser 50 caractères")
+ private String numeroIdentite;
+
+ @Size(max = 20, message = "Le type d'identité ne peut pas dépasser 20 caractères")
+ private String typeIdentite;
+
+ @NotNull(message = "Le statut est obligatoire")
+ private String statut;
+
+ @NotNull(message = "L'association est obligatoire")
+ private Long associationId;
+
+ private String associationNom;
+
+ @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss")
+ private LocalDateTime dateInscription;
+
+ @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss")
+ private LocalDateTime dateDerniereModification;
+
+ private String creePar;
+ private String modifiePar;
+
+ // Constructeurs
+ public MembreDTO() {}
+
+ public MembreDTO(String numeroMembre, String nom, String prenom, String email) {
+ this.numeroMembre = numeroMembre;
+ this.nom = nom;
+ this.prenom = prenom;
+ this.email = email;
+ this.statut = "ACTIF";
+ this.dateInscription = LocalDateTime.now();
+ }
+
+ // Getters et Setters
+ public Long getId() { return id; }
+ public void setId(Long id) { this.id = id; }
+
+ public String getNumeroMembre() { return numeroMembre; }
+ public void setNumeroMembre(String numeroMembre) { this.numeroMembre = numeroMembre; }
+
+ public String getNom() { return nom; }
+ public void setNom(String nom) { this.nom = nom; }
+
+ public String getPrenom() { return prenom; }
+ public void setPrenom(String prenom) { this.prenom = prenom; }
+
+ public String getEmail() { return email; }
+ public void setEmail(String email) { this.email = email; }
+
+ public String getTelephone() { return telephone; }
+ public void setTelephone(String telephone) { this.telephone = telephone; }
+
+ public LocalDate getDateNaissance() { return dateNaissance; }
+ public void setDateNaissance(LocalDate dateNaissance) { this.dateNaissance = dateNaissance; }
+
+ public String getAdresse() { return adresse; }
+ public void setAdresse(String adresse) { this.adresse = adresse; }
+
+ public String getProfession() { return profession; }
+ public void setProfession(String profession) { this.profession = profession; }
+
+ public String getStatutMatrimonial() { return statutMatrimonial; }
+ public void setStatutMatrimonial(String statutMatrimonial) { this.statutMatrimonial = statutMatrimonial; }
+
+ public String getNationalite() { return nationalite; }
+ public void setNationalite(String nationalite) { this.nationalite = nationalite; }
+
+ public String getNumeroIdentite() { return numeroIdentite; }
+ public void setNumeroIdentite(String numeroIdentite) { this.numeroIdentite = numeroIdentite; }
+
+ public String getTypeIdentite() { return typeIdentite; }
+ public void setTypeIdentite(String typeIdentite) { this.typeIdentite = typeIdentite; }
+
+ public String getStatut() { return statut; }
+ public void setStatut(String statut) { this.statut = statut; }
+
+ public Long getAssociationId() { return associationId; }
+ public void setAssociationId(Long associationId) { this.associationId = associationId; }
+
+ public String getAssociationNom() { return associationNom; }
+ public void setAssociationNom(String associationNom) { this.associationNom = associationNom; }
+
+ public LocalDateTime getDateInscription() { return dateInscription; }
+ public void setDateInscription(LocalDateTime dateInscription) { this.dateInscription = dateInscription; }
+
+ public LocalDateTime getDateDerniereModification() { return dateDerniereModification; }
+ public void setDateDerniereModification(LocalDateTime dateDerniereModification) { this.dateDerniereModification = dateDerniereModification; }
+
+ public String getCreePar() { return creePar; }
+ public void setCreePar(String creePar) { this.creePar = creePar; }
+
+ public String getModifiePar() { return modifiePar; }
+ public void setModifiePar(String modifiePar) { this.modifiePar = modifiePar; }
+
+ // Propriétés dérivées
+ public String getNomComplet() {
+ return (prenom != null ? prenom : "") + " " + (nom != null ? nom : "");
+ }
+
+ public String getStatutLibelle() {
+ return switch (statut != null ? statut : "") {
+ case "ACTIF" -> "Actif";
+ case "INACTIF" -> "Inactif";
+ case "SUSPENDU" -> "Suspendu";
+ case "RADIE" -> "Radié";
+ default -> statut;
+ };
+ }
+
+ public String getStatutSeverity() {
+ return switch (statut != null ? statut : "") {
+ case "ACTIF" -> "success";
+ case "INACTIF" -> "warning";
+ case "SUSPENDU" -> "danger";
+ case "RADIE" -> "secondary";
+ default -> "info";
+ };
+ }
+
+ @Override
+ public String toString() {
+ return "MembreDTO{" +
+ "id=" + id +
+ ", numeroMembre='" + numeroMembre + '\'' +
+ ", nom='" + nom + '\'' +
+ ", prenom='" + prenom + '\'' +
+ ", email='" + email + '\'' +
+ ", statut='" + statut + '\'' +
+ '}';
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/dto/SouscriptionDTO.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/dto/SouscriptionDTO.java
new file mode 100644
index 0000000..3fbbdc1
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/dto/SouscriptionDTO.java
@@ -0,0 +1,240 @@
+package dev.lions.unionflow.client.dto;
+
+import jakarta.validation.constraints.NotNull;
+import java.io.Serializable;
+import java.math.BigDecimal;
+import java.time.LocalDate;
+import java.time.LocalDateTime;
+
+public class SouscriptionDTO implements Serializable {
+
+ private static final long serialVersionUID = 1L;
+
+ public enum StatutSouscription {
+ ACTIVE("Actif", "text-green-600", "bg-green-100"),
+ SUSPENDUE("Suspendue", "text-orange-600", "bg-orange-100"),
+ EXPIREE("Expirée", "text-red-600", "bg-red-100"),
+ EN_ATTENTE_PAIEMENT("En attente de paiement", "text-blue-600", "bg-blue-100"),
+ ANNULEE("Annulée", "text-gray-600", "bg-gray-100");
+
+ private final String libelle;
+ private final String couleurTexte;
+ private final String couleurFond;
+
+ StatutSouscription(String libelle, String couleurTexte, String couleurFond) {
+ this.libelle = libelle;
+ this.couleurTexte = couleurTexte;
+ this.couleurFond = couleurFond;
+ }
+
+ public String getLibelle() { return libelle; }
+ public String getCouleurTexte() { return couleurTexte; }
+ public String getCouleurFond() { return couleurFond; }
+ }
+
+ public enum TypeFacturation {
+ MENSUEL("Mensuel"),
+ ANNUEL("Annuel");
+
+ private final String libelle;
+
+ TypeFacturation(String libelle) {
+ this.libelle = libelle;
+ }
+
+ public String getLibelle() { return libelle; }
+ }
+
+ private Long id;
+
+ @NotNull
+ private Long organisationId;
+ private String organisationNom;
+
+ @NotNull
+ private Long formulaireId;
+ private String formulaireNom;
+
+ @NotNull
+ private StatutSouscription statut;
+
+ @NotNull
+ private TypeFacturation typeFacturation;
+
+ @NotNull
+ private LocalDate dateDebut;
+
+ @NotNull
+ private LocalDate dateFin;
+
+ private LocalDate dateDernierPaiement;
+ private LocalDate dateProchainPaiement;
+
+ @NotNull
+ private Integer quotaMaxMembres;
+
+ private Integer membresActuels = 0;
+
+ @NotNull
+ private BigDecimal montantSouscription;
+
+ private String deviseCode = "XOF";
+
+ private String numeroFacture;
+ private String referencePaiement;
+
+ // Informations de renouvellement automatique
+ private boolean renouvellementAutomatique = false;
+ private String methodePaiementDefaut;
+
+ // Notifications
+ private boolean notificationExpiration = true;
+ private boolean notificationQuotaAtteint = true;
+ private int joursAvantNotificationExpiration = 30;
+
+ // Audit
+ private LocalDateTime dateCreation;
+ private LocalDateTime dateMiseAJour;
+ private String creePar;
+ private String modifiePar;
+
+ public SouscriptionDTO() {}
+
+ // Getters et Setters
+ public Long getId() { return id; }
+ public void setId(Long id) { this.id = id; }
+
+ public Long getOrganisationId() { return organisationId; }
+ public void setOrganisationId(Long organisationId) { this.organisationId = organisationId; }
+
+ public String getOrganisationNom() { return organisationNom; }
+ public void setOrganisationNom(String organisationNom) { this.organisationNom = organisationNom; }
+
+ public Long getFormulaireId() { return formulaireId; }
+ public void setFormulaireId(Long formulaireId) { this.formulaireId = formulaireId; }
+
+ public String getFormulaireNom() { return formulaireNom; }
+ public void setFormulaireNom(String formulaireNom) { this.formulaireNom = formulaireNom; }
+
+ public StatutSouscription getStatut() { return statut; }
+ public void setStatut(StatutSouscription statut) { this.statut = statut; }
+
+ public TypeFacturation getTypeFacturation() { return typeFacturation; }
+ public void setTypeFacturation(TypeFacturation typeFacturation) { this.typeFacturation = typeFacturation; }
+
+ public LocalDate getDateDebut() { return dateDebut; }
+ public void setDateDebut(LocalDate dateDebut) { this.dateDebut = dateDebut; }
+
+ public LocalDate getDateFin() { return dateFin; }
+ public void setDateFin(LocalDate dateFin) { this.dateFin = dateFin; }
+
+ public LocalDate getDateDernierPaiement() { return dateDernierPaiement; }
+ public void setDateDernierPaiement(LocalDate dateDernierPaiement) { this.dateDernierPaiement = dateDernierPaiement; }
+
+ public LocalDate getDateProchainPaiement() { return dateProchainPaiement; }
+ public void setDateProchainPaiement(LocalDate dateProchainPaiement) { this.dateProchainPaiement = dateProchainPaiement; }
+
+ public Integer getQuotaMaxMembres() { return quotaMaxMembres; }
+ public void setQuotaMaxMembres(Integer quotaMaxMembres) { this.quotaMaxMembres = quotaMaxMembres; }
+
+ public Integer getMembresActuels() { return membresActuels; }
+ public void setMembresActuels(Integer membresActuels) { this.membresActuels = membresActuels; }
+
+ public BigDecimal getMontantSouscription() { return montantSouscription; }
+ public void setMontantSouscription(BigDecimal montantSouscription) { this.montantSouscription = montantSouscription; }
+
+ public String getDeviseCode() { return deviseCode; }
+ public void setDeviseCode(String deviseCode) { this.deviseCode = deviseCode; }
+
+ public String getNumeroFacture() { return numeroFacture; }
+ public void setNumeroFacture(String numeroFacture) { this.numeroFacture = numeroFacture; }
+
+ public String getReferencePaiement() { return referencePaiement; }
+ public void setReferencePaiement(String referencePaiement) { this.referencePaiement = referencePaiement; }
+
+ public boolean isRenouvellementAutomatique() { return renouvellementAutomatique; }
+ public void setRenouvellementAutomatique(boolean renouvellementAutomatique) { this.renouvellementAutomatique = renouvellementAutomatique; }
+
+ public String getMethodePaiementDefaut() { return methodePaiementDefaut; }
+ public void setMethodePaiementDefaut(String methodePaiementDefaut) { this.methodePaiementDefaut = methodePaiementDefaut; }
+
+ public boolean isNotificationExpiration() { return notificationExpiration; }
+ public void setNotificationExpiration(boolean notificationExpiration) { this.notificationExpiration = notificationExpiration; }
+
+ public boolean isNotificationQuotaAtteint() { return notificationQuotaAtteint; }
+ public void setNotificationQuotaAtteint(boolean notificationQuotaAtteint) { this.notificationQuotaAtteint = notificationQuotaAtteint; }
+
+ public int getJoursAvantNotificationExpiration() { return joursAvantNotificationExpiration; }
+ public void setJoursAvantNotificationExpiration(int joursAvantNotificationExpiration) { this.joursAvantNotificationExpiration = joursAvantNotificationExpiration; }
+
+ public LocalDateTime getDateCreation() { return dateCreation; }
+ public void setDateCreation(LocalDateTime dateCreation) { this.dateCreation = dateCreation; }
+
+ public LocalDateTime getDateMiseAJour() { return dateMiseAJour; }
+ public void setDateMiseAJour(LocalDateTime dateMiseAJour) { this.dateMiseAJour = dateMiseAJour; }
+
+ public String getCreePar() { return creePar; }
+ public void setCreePar(String creePar) { this.creePar = creePar; }
+
+ public String getModifiePar() { return modifiePar; }
+ public void setModifiePar(String modifiePar) { this.modifiePar = modifiePar; }
+
+ // Méthodes utilitaires
+ public boolean isActive() {
+ return statut == StatutSouscription.ACTIVE && !isExpiree();
+ }
+
+ public boolean isExpiree() {
+ return LocalDate.now().isAfter(dateFin);
+ }
+
+ public boolean isQuotaAtteint() {
+ return membresActuels != null && quotaMaxMembres != null &&
+ membresActuels >= quotaMaxMembres;
+ }
+
+ public int getMembresRestants() {
+ if (membresActuels != null && quotaMaxMembres != null) {
+ return Math.max(0, quotaMaxMembres - membresActuels);
+ }
+ return 0;
+ }
+
+ public int getPourcentageUtilisation() {
+ if (membresActuels != null && quotaMaxMembres != null && quotaMaxMembres > 0) {
+ return (membresActuels * 100) / quotaMaxMembres;
+ }
+ return 0;
+ }
+
+ public String getMontantFormat() {
+ if (montantSouscription != null) {
+ return String.format("%,.0f %s", montantSouscription, deviseCode);
+ }
+ return "0 " + deviseCode;
+ }
+
+ public String getStatutCouleurClass() {
+ return statut != null ? statut.getCouleurTexte() : "text-gray-600";
+ }
+
+ public String getStatutFondClass() {
+ return statut != null ? statut.getCouleurFond() : "bg-gray-100";
+ }
+
+ public String getStatutLibelle() {
+ return statut != null ? statut.getLibelle() : "Inconnu";
+ }
+
+ public long getJoursRestants() {
+ if (dateFin != null) {
+ return LocalDate.now().until(dateFin).getDays();
+ }
+ return 0;
+ }
+
+ public boolean isExpirationProche() {
+ long joursRestants = getJoursRestants();
+ return joursRestants <= joursAvantNotificationExpiration && joursRestants > 0;
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/dto/auth/LoginRequest.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/dto/auth/LoginRequest.java
new file mode 100644
index 0000000..0d9afc9
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/dto/auth/LoginRequest.java
@@ -0,0 +1,60 @@
+package dev.lions.unionflow.client.dto.auth;
+
+import jakarta.validation.constraints.NotBlank;
+import jakarta.validation.constraints.Size;
+
+public class 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")
+ private 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")
+ private String password;
+
+ @NotBlank(message = "Le type de compte est requis")
+ private String typeCompte;
+
+ private boolean rememberMe;
+
+ public LoginRequest() {}
+
+ public LoginRequest(String username, String password, String typeCompte) {
+ this.username = username;
+ this.password = password;
+ this.typeCompte = typeCompte;
+ }
+
+ public String getUsername() {
+ return username;
+ }
+
+ public void setUsername(String username) {
+ this.username = username;
+ }
+
+ public String getPassword() {
+ return password;
+ }
+
+ public void setPassword(String password) {
+ this.password = password;
+ }
+
+ public String getTypeCompte() {
+ return typeCompte;
+ }
+
+ public void setTypeCompte(String typeCompte) {
+ this.typeCompte = typeCompte;
+ }
+
+ public boolean isRememberMe() {
+ return rememberMe;
+ }
+
+ public void setRememberMe(boolean rememberMe) {
+ this.rememberMe = rememberMe;
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/dto/auth/LoginResponse.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/dto/auth/LoginResponse.java
new file mode 100644
index 0000000..2626d19
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/dto/auth/LoginResponse.java
@@ -0,0 +1,223 @@
+package dev.lions.unionflow.client.dto.auth;
+
+import java.time.LocalDateTime;
+import java.util.List;
+
+public class LoginResponse {
+
+ private String accessToken;
+ private String refreshToken;
+ private String tokenType = "Bearer";
+ private Long expiresIn;
+ private LocalDateTime expirationDate;
+
+ private UserInfo user;
+
+ public LoginResponse() {}
+
+ public LoginResponse(String accessToken, String refreshToken, Long expiresIn, UserInfo user) {
+ this.accessToken = accessToken;
+ this.refreshToken = refreshToken;
+ this.expiresIn = expiresIn;
+ this.user = user;
+ this.expirationDate = LocalDateTime.now().plusSeconds(expiresIn);
+ }
+
+ public String getAccessToken() {
+ return accessToken;
+ }
+
+ public void setAccessToken(String accessToken) {
+ this.accessToken = accessToken;
+ }
+
+ public String getRefreshToken() {
+ return refreshToken;
+ }
+
+ public void setRefreshToken(String refreshToken) {
+ this.refreshToken = refreshToken;
+ }
+
+ public String getTokenType() {
+ return tokenType;
+ }
+
+ public void setTokenType(String tokenType) {
+ this.tokenType = tokenType;
+ }
+
+ public Long getExpiresIn() {
+ return expiresIn;
+ }
+
+ public void setExpiresIn(Long expiresIn) {
+ this.expiresIn = expiresIn;
+ if (expiresIn != null) {
+ this.expirationDate = LocalDateTime.now().plusSeconds(expiresIn);
+ }
+ }
+
+ public LocalDateTime getExpirationDate() {
+ return expirationDate;
+ }
+
+ public void setExpirationDate(LocalDateTime expirationDate) {
+ this.expirationDate = expirationDate;
+ }
+
+ public UserInfo getUser() {
+ return user;
+ }
+
+ public void setUser(UserInfo user) {
+ this.user = user;
+ }
+
+ public boolean isExpired() {
+ return expirationDate != null && LocalDateTime.now().isAfter(expirationDate);
+ }
+
+ public static class UserInfo {
+ private Long 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;
+
+ public UserInfo() {}
+
+ public Long getId() {
+ return id;
+ }
+
+ public void setId(Long id) {
+ this.id = id;
+ }
+
+ public String getNom() {
+ return nom;
+ }
+
+ public void setNom(String nom) {
+ this.nom = nom;
+ }
+
+ public String getPrenom() {
+ return prenom;
+ }
+
+ public void setPrenom(String prenom) {
+ this.prenom = prenom;
+ }
+
+ public String getEmail() {
+ return email;
+ }
+
+ public void setEmail(String email) {
+ this.email = email;
+ }
+
+ public String getUsername() {
+ return username;
+ }
+
+ public void setUsername(String username) {
+ this.username = username;
+ }
+
+ public String getTypeCompte() {
+ return typeCompte;
+ }
+
+ public void setTypeCompte(String typeCompte) {
+ this.typeCompte = typeCompte;
+ }
+
+ public List getRoles() {
+ return roles;
+ }
+
+ public void setRoles(List roles) {
+ this.roles = roles;
+ }
+
+ public List getPermissions() {
+ return permissions;
+ }
+
+ public void setPermissions(List permissions) {
+ this.permissions = permissions;
+ }
+
+ public EntiteInfo getEntite() {
+ return entite;
+ }
+
+ public void setEntite(EntiteInfo entite) {
+ this.entite = entite;
+ }
+
+ public String getNomComplet() {
+ if (prenom != null && nom != null) {
+ return prenom + " " + nom;
+ }
+ return nom != null ? nom : username;
+ }
+ }
+
+ public static class EntiteInfo {
+ private Long id;
+ private String nom;
+ private String type;
+ private String pays;
+ private String ville;
+
+ public EntiteInfo() {}
+
+ public Long getId() {
+ return id;
+ }
+
+ public void setId(Long id) {
+ this.id = id;
+ }
+
+ public String getNom() {
+ return nom;
+ }
+
+ public void setNom(String nom) {
+ this.nom = nom;
+ }
+
+ public String getType() {
+ return type;
+ }
+
+ public void setType(String type) {
+ this.type = type;
+ }
+
+ public String getPays() {
+ return pays;
+ }
+
+ public void setPays(String pays) {
+ this.pays = pays;
+ }
+
+ public String getVille() {
+ return ville;
+ }
+
+ public void setVille(String ville) {
+ this.ville = ville;
+ }
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/exception/ViewExpiredExceptionHandler.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/exception/ViewExpiredExceptionHandler.java
new file mode 100644
index 0000000..758cfd0
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/exception/ViewExpiredExceptionHandler.java
@@ -0,0 +1,87 @@
+package dev.lions.unionflow.client.exception;
+
+import jakarta.faces.FacesException;
+import jakarta.faces.application.NavigationHandler;
+import jakarta.faces.application.ViewExpiredException;
+import jakarta.faces.context.ExceptionHandler;
+import jakarta.faces.context.ExceptionHandlerWrapper;
+import jakarta.faces.context.FacesContext;
+import jakarta.faces.event.ExceptionQueuedEvent;
+import jakarta.faces.event.ExceptionQueuedEventContext;
+import java.util.Iterator;
+import java.util.Map;
+import java.util.logging.Level;
+import java.util.logging.Logger;
+
+public class ViewExpiredExceptionHandler extends ExceptionHandlerWrapper {
+
+ private static final Logger LOG = Logger.getLogger(ViewExpiredExceptionHandler.class.getName());
+ private ExceptionHandler wrapped;
+
+ public ViewExpiredExceptionHandler(ExceptionHandler wrapped) {
+ this.wrapped = wrapped;
+ }
+
+ @Override
+ public ExceptionHandler getWrapped() {
+ return wrapped;
+ }
+
+ @Override
+ public void handle() throws FacesException {
+ Iterator iterator = getUnhandledExceptionQueuedEvents().iterator();
+
+ while (iterator.hasNext()) {
+ ExceptionQueuedEvent event = iterator.next();
+ ExceptionQueuedEventContext context = (ExceptionQueuedEventContext) event.getSource();
+ Throwable throwable = context.getException();
+
+ if (throwable instanceof ViewExpiredException) {
+ ViewExpiredException vee = (ViewExpiredException) throwable;
+ FacesContext facesContext = FacesContext.getCurrentInstance();
+
+ try {
+ LOG.log(Level.INFO, "ViewExpiredException interceptée pour la vue: {0}", vee.getViewId());
+
+ // Vérifier que FacesContext et ExternalContext sont disponibles
+ if (facesContext != null && facesContext.getExternalContext() != null) {
+ // Stocker l'URL demandée pour redirection après connexion si possible
+ String originalURL = vee.getViewId();
+ try {
+ if (facesContext.getExternalContext().getSessionMap() != null) {
+ facesContext.getExternalContext().getSessionMap().put("redirectURL", originalURL);
+ }
+ } catch (Exception e) {
+ LOG.log(Level.WARNING, "Impossible de stocker l'URL de redirection: {0}", e.getMessage());
+ }
+
+ // Rediriger vers la page de login avec paramètre expired
+ try {
+ String redirectURL = "/pages/public/login.xhtml?expired=true";
+ facesContext.getExternalContext().redirect(
+ facesContext.getExternalContext().getRequestContextPath() + redirectURL
+ );
+ facesContext.responseComplete();
+ } catch (Exception e) {
+ LOG.log(Level.SEVERE, "Erreur lors de la redirection: {0}", e.getMessage());
+ // Fallback: essayer une redirection simple
+ try {
+ facesContext.getExternalContext().redirect("/pages/public/login.xhtml");
+ facesContext.responseComplete();
+ } catch (Exception fallbackException) {
+ LOG.log(Level.SEVERE, "Impossible de rediriger vers login: {0}", fallbackException.getMessage());
+ }
+ }
+ }
+ } catch (Exception e) {
+ LOG.log(Level.SEVERE, "Erreur dans ViewExpiredExceptionHandler: {0}", e.getMessage());
+ } finally {
+ iterator.remove();
+ }
+ }
+ }
+
+ // Laisser le parent gérer les autres exceptions
+ getWrapped().handle();
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/exception/ViewExpiredExceptionHandlerFactory.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/exception/ViewExpiredExceptionHandlerFactory.java
new file mode 100644
index 0000000..1d27c6a
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/exception/ViewExpiredExceptionHandlerFactory.java
@@ -0,0 +1,18 @@
+package dev.lions.unionflow.client.exception;
+
+import jakarta.faces.context.ExceptionHandler;
+import jakarta.faces.context.ExceptionHandlerFactory;
+
+public class ViewExpiredExceptionHandlerFactory extends ExceptionHandlerFactory {
+
+ private ExceptionHandlerFactory parent;
+
+ public ViewExpiredExceptionHandlerFactory(ExceptionHandlerFactory parent) {
+ this.parent = parent;
+ }
+
+ @Override
+ public ExceptionHandler getExceptionHandler() {
+ return new ViewExpiredExceptionHandler(parent.getExceptionHandler());
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/security/AuthenticationFilter.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/security/AuthenticationFilter.java
new file mode 100644
index 0000000..5e1b016
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/security/AuthenticationFilter.java
@@ -0,0 +1,89 @@
+package dev.lions.unionflow.client.security;
+
+import dev.lions.unionflow.client.view.UserSession;
+import jakarta.inject.Inject;
+import jakarta.servlet.*;
+import jakarta.servlet.annotation.WebFilter;
+import jakarta.servlet.http.HttpServletRequest;
+import jakarta.servlet.http.HttpServletResponse;
+import java.io.IOException;
+import java.util.logging.Logger;
+
+@WebFilter(urlPatterns = {"/pages/secure/*", "/pages/admin/*", "/pages/super-admin/*", "/pages/membre/*"})
+public class AuthenticationFilter implements Filter {
+
+ private static final Logger LOGGER = Logger.getLogger(AuthenticationFilter.class.getName());
+
+ @Inject
+ private UserSession userSession;
+
+ @Inject
+ private JwtTokenManager tokenManager;
+
+ @Override
+ public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain)
+ throws IOException, ServletException {
+
+ HttpServletRequest httpRequest = (HttpServletRequest) request;
+ HttpServletResponse httpResponse = (HttpServletResponse) response;
+
+ String requestURI = httpRequest.getRequestURI();
+
+ // Vérifier si l'utilisateur est authentifié
+ if (!isAuthenticated()) {
+ LOGGER.warning("Accès non autorisé à: " + requestURI);
+ httpResponse.sendRedirect(httpRequest.getContextPath() + "/pages/public/login.xhtml");
+ return;
+ }
+
+ // Vérifier les autorisations spécifiques
+ if (!hasRequiredPermissions(requestURI)) {
+ LOGGER.warning("Permissions insuffisantes pour: " + requestURI +
+ " (Utilisateur: " + userSession.getUsername() +
+ ", Type: " + userSession.getTypeCompte() + ")");
+ httpResponse.sendRedirect(httpRequest.getContextPath() + "/pages/secure/access-denied.xhtml");
+ return;
+ }
+
+ // Continuer la chaîne de filtres
+ chain.doFilter(request, response);
+ }
+
+ private boolean isAuthenticated() {
+ return userSession != null &&
+ userSession.isAuthenticated() &&
+ tokenManager != null &&
+ tokenManager.hasValidTokens();
+ }
+
+ private boolean hasRequiredPermissions(String requestURI) {
+ if (requestURI.contains("/pages/super-admin/")) {
+ return userSession.isSuperAdmin();
+ }
+
+ if (requestURI.contains("/pages/admin/")) {
+ return userSession.isAdmin();
+ }
+
+ if (requestURI.contains("/pages/membre/")) {
+ return userSession.isMembre();
+ }
+
+ // Pages sécurisées générales - tout utilisateur authentifié
+ if (requestURI.contains("/pages/secure/")) {
+ return true;
+ }
+
+ return false;
+ }
+
+ @Override
+ public void init(FilterConfig filterConfig) throws ServletException {
+ LOGGER.info("Filtre d'authentification initialisé");
+ }
+
+ @Override
+ public void destroy() {
+ LOGGER.info("Filtre d'authentification détruit");
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/security/JwtClientRequestFilter.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/security/JwtClientRequestFilter.java
new file mode 100644
index 0000000..bb508c6
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/security/JwtClientRequestFilter.java
@@ -0,0 +1,39 @@
+package dev.lions.unionflow.client.security;
+
+import jakarta.annotation.Priority;
+import jakarta.inject.Inject;
+import jakarta.ws.rs.client.ClientRequestContext;
+import jakarta.ws.rs.client.ClientRequestFilter;
+import jakarta.ws.rs.core.HttpHeaders;
+import jakarta.ws.rs.ext.Provider;
+import java.io.IOException;
+import java.util.logging.Logger;
+
+@Provider
+@Priority(1000)
+public class JwtClientRequestFilter implements ClientRequestFilter {
+
+ private static final Logger LOGGER = Logger.getLogger(JwtClientRequestFilter.class.getName());
+
+ @Inject
+ private JwtTokenManager tokenManager;
+
+ @Override
+ public void filter(ClientRequestContext requestContext) throws IOException {
+ String authHeader = tokenManager.getAuthorizationHeader();
+
+ if (authHeader != null && !isAuthEndpoint(requestContext.getUri().getPath())) {
+ requestContext.getHeaders().add(HttpHeaders.AUTHORIZATION, authHeader);
+ LOGGER.fine("JWT token ajouté à la requête: " + requestContext.getUri());
+ }
+ }
+
+ private boolean isAuthEndpoint(String path) {
+ return path != null && (
+ path.contains("/auth/login") ||
+ path.contains("/auth/register") ||
+ path.contains("/auth/refresh") ||
+ path.contains("/public/")
+ );
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/security/JwtTokenManager.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/security/JwtTokenManager.java
new file mode 100644
index 0000000..19b7a81
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/security/JwtTokenManager.java
@@ -0,0 +1,129 @@
+package dev.lions.unionflow.client.security;
+
+import dev.lions.unionflow.client.dto.auth.LoginResponse;
+import jakarta.enterprise.context.SessionScoped;
+import jakarta.faces.context.FacesContext;
+import jakarta.inject.Inject;
+import jakarta.inject.Named;
+import java.io.Serializable;
+import java.time.LocalDateTime;
+import java.util.logging.Logger;
+
+@Named("jwtTokenManager")
+@SessionScoped
+public class JwtTokenManager implements Serializable {
+
+ private static final Logger LOGGER = Logger.getLogger(JwtTokenManager.class.getName());
+
+ @Inject
+ private TokenRefreshService tokenRefreshService;
+
+ private String accessToken;
+ private String refreshToken;
+ private LocalDateTime expirationDate;
+ private String tokenType = "Bearer";
+
+ public void setTokens(LoginResponse loginResponse) {
+ this.accessToken = loginResponse.getAccessToken();
+ this.refreshToken = loginResponse.getRefreshToken();
+ this.expirationDate = loginResponse.getExpirationDate();
+ this.tokenType = loginResponse.getTokenType();
+
+ // Enregistrer le token dans le service global
+ String sessionId = getSessionId();
+ if (sessionId != null) {
+ tokenRefreshService.registerToken(sessionId,
+ this.accessToken,
+ this.refreshToken,
+ loginResponse.getExpiresIn());
+ }
+
+ LOGGER.info("Tokens JWT mis à jour. Expiration: " + expirationDate);
+ }
+
+ public String getAccessToken() {
+ return accessToken;
+ }
+
+ public String getRefreshToken() {
+ return refreshToken;
+ }
+
+ public String getAuthorizationHeader() {
+ if (accessToken != null) {
+ return tokenType + " " + accessToken;
+ }
+ return null;
+ }
+
+ public boolean isTokenValid() {
+ if (accessToken == null || expirationDate == null) {
+ return false;
+ }
+
+ // Considérer le token comme expiré 30 secondes avant l'expiration réelle
+ LocalDateTime expirationWithBuffer = expirationDate.minusSeconds(30);
+ return LocalDateTime.now().isBefore(expirationWithBuffer);
+ }
+
+ public boolean needsRefresh() {
+ if (accessToken == null || expirationDate == null) {
+ return false;
+ }
+
+ // Rafraîchir le token 5 minutes avant l'expiration
+ LocalDateTime refreshThreshold = expirationDate.minusMinutes(5);
+ return LocalDateTime.now().isAfter(refreshThreshold);
+ }
+
+ public long getTimeUntilExpiration() {
+ if (expirationDate == null) {
+ return 0;
+ }
+
+ LocalDateTime now = LocalDateTime.now();
+ if (now.isAfter(expirationDate)) {
+ return 0;
+ }
+
+ return java.time.Duration.between(now, expirationDate).getSeconds();
+ }
+
+ public void clearTokens() {
+ this.accessToken = null;
+ this.refreshToken = null;
+ this.expirationDate = null;
+
+ // Supprimer le token du service global
+ String sessionId = getSessionId();
+ if (sessionId != null) {
+ tokenRefreshService.removeToken(sessionId);
+ }
+
+ LOGGER.info("Tokens JWT supprimés");
+ }
+
+ private String getSessionId() {
+ try {
+ FacesContext facesContext = FacesContext.getCurrentInstance();
+ if (facesContext != null && facesContext.getExternalContext() != null) {
+ return facesContext.getExternalContext().getSessionId(false);
+ }
+ } catch (Exception e) {
+ LOGGER.fine("Impossible de récupérer l'ID de session: " + e.getMessage());
+ }
+ return null;
+ }
+
+ public boolean hasValidTokens() {
+ return accessToken != null && refreshToken != null && isTokenValid();
+ }
+
+ public LocalDateTime getExpirationDate() {
+ return expirationDate;
+ }
+
+ public String getTokenType() {
+ return tokenType;
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/security/PermissionChecker.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/security/PermissionChecker.java
new file mode 100644
index 0000000..f44170a
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/security/PermissionChecker.java
@@ -0,0 +1,239 @@
+package dev.lions.unionflow.client.security;
+
+import dev.lions.unionflow.client.view.UserSession;
+import jakarta.enterprise.context.RequestScoped;
+import jakarta.inject.Inject;
+import jakarta.inject.Named;
+import java.io.Serializable;
+
+@Named("permissionChecker")
+@RequestScoped
+public class PermissionChecker implements Serializable {
+
+ private static final long serialVersionUID = 1L;
+
+ @Inject
+ private UserSession userSession;
+
+ // Vérifications basées sur le rôle utilisateur
+ public boolean hasRole(String role) {
+ if (userSession == null || !userSession.isAuthenticated()) {
+ return false;
+ }
+
+ String userRole = userSession.getRole();
+ return role.equals(userRole);
+ }
+
+ public boolean hasAnyRole(String... roles) {
+ if (userSession == null || !userSession.isAuthenticated()) {
+ return false;
+ }
+
+ String userRole = userSession.getRole();
+ for (String role : roles) {
+ if (role.equals(userRole)) {
+ return true;
+ }
+ }
+ return false;
+ }
+
+ // Vérifications basées sur les permissions
+ public boolean canManageMembers() {
+ return hasAnyRole("ADMIN", "GESTIONNAIRE_MEMBRE");
+ }
+
+ public boolean canValidateMembers() {
+ return hasAnyRole("ADMIN", "GESTIONNAIRE_MEMBRE");
+ }
+
+ public boolean canManageFinances() {
+ return hasAnyRole("ADMIN", "TRESORIER", "GESTIONNAIRE_FINANCE");
+ }
+
+ public boolean canManageEvents() {
+ return hasAnyRole("ADMIN", "GESTIONNAIRE_EVENEMENT");
+ }
+
+ public boolean canManageAides() {
+ return hasAnyRole("ADMIN", "GESTIONNAIRE_AIDE");
+ }
+
+ public boolean canViewReports() {
+ return hasAnyRole("ADMIN", "GESTIONNAIRE_MEMBRE", "TRESORIER");
+ }
+
+ public boolean canManageSubscription() {
+ return hasRole("ADMIN");
+ }
+
+ public boolean canManageOrganization() {
+ return hasRole("ADMIN");
+ }
+
+ public boolean canAccessSuperAdmin() {
+ return hasRole("SUPER_ADMIN");
+ }
+
+ // Vérifications basées sur les fonctionnalités du forfait
+ public boolean isFeatureEnabled(String feature) {
+ // Cette méthode vérifiera si la fonctionnalité est incluse dans le forfait souscrit
+ // Pour l'instant, simulation basée sur des rôles
+
+ switch (feature.toLowerCase()) {
+ case "gestion_membres":
+ return true; // Toujours disponible
+
+ case "gestion_cotisations":
+ return true; // Toujours disponible
+
+ case "gestion_evenements":
+ return !hasRole("MEMBER"); // Pas pour les membres simples
+
+ case "gestion_aides":
+ return hasAnyRole("ADMIN", "GESTIONNAIRE_AIDE");
+
+ case "rapports_avances":
+ return hasAnyRole("ADMIN", "SUPER_ADMIN");
+
+ case "integration_paiement":
+ return hasAnyRole("ADMIN", "TRESORIER");
+
+ case "notifications_sms":
+ return hasAnyRole("ADMIN", "SUPER_ADMIN");
+
+ case "gestion_documents":
+ return hasAnyRole("ADMIN", "GESTIONNAIRE_MEMBRE");
+
+ case "support_prioritaire":
+ return hasAnyRole("ADMIN", "SUPER_ADMIN");
+
+ case "personnalisation_avancee":
+ return hasRole("SUPER_ADMIN");
+
+ default:
+ return false;
+ }
+ }
+
+ // Vérifications pour l'interface utilisateur
+ public boolean showCreateMemberButton() {
+ return canManageMembers() && isFeatureEnabled("gestion_membres");
+ }
+
+ public boolean showValidateMemberButton() {
+ return canValidateMembers() && isFeatureEnabled("gestion_membres");
+ }
+
+ public boolean showFinancialSection() {
+ return canManageFinances() && isFeatureEnabled("gestion_cotisations");
+ }
+
+ public boolean showEventsSection() {
+ return canManageEvents() && isFeatureEnabled("gestion_evenements");
+ }
+
+ public boolean showAidesSection() {
+ return canManageAides() && isFeatureEnabled("gestion_aides");
+ }
+
+ public boolean showReportsSection() {
+ return canViewReports() && isFeatureEnabled("rapports_avances");
+ }
+
+ public boolean showSubscriptionManagement() {
+ return canManageSubscription();
+ }
+
+ public boolean showAdvancedSettings() {
+ return canManageOrganization() && isFeatureEnabled("personnalisation_avancee");
+ }
+
+ public boolean showSuperAdminFeatures() {
+ return canAccessSuperAdmin();
+ }
+
+ // Vérifications spécifiques aux actions
+ public boolean canCreateEvent() {
+ return canManageEvents() && isFeatureEnabled("gestion_evenements");
+ }
+
+ public boolean canProcessAideRequest() {
+ return canManageAides() && isFeatureEnabled("gestion_aides");
+ }
+
+ public boolean canExportData() {
+ return canViewReports() && isFeatureEnabled("rapports_avances");
+ }
+
+ public boolean canSendNotifications() {
+ return canManageMembers() && (isFeatureEnabled("notifications_email") || isFeatureEnabled("notifications_sms"));
+ }
+
+ public boolean canManageDocuments() {
+ return canManageMembers() && isFeatureEnabled("gestion_documents");
+ }
+
+ // Vérifications pour les limites
+ public boolean canAddNewMember() {
+ if (!canManageMembers()) {
+ return false;
+ }
+
+ // Vérifier le quota de membres (sera implémenté avec SouscriptionBean)
+ // Pour l'instant, toujours vrai si on a les permissions
+ return true;
+ }
+
+ // Méthodes utilitaires pour l'affichage conditionnel
+ public String getRoleBasedStyleClass() {
+ if (!userSession.isAuthenticated()) {
+ return "guest-mode";
+ }
+
+ String role = userSession.getRole();
+ switch (role) {
+ case "SUPER_ADMIN":
+ return "super-admin-mode";
+ case "ADMIN":
+ return "admin-mode";
+ case "GESTIONNAIRE_MEMBRE":
+ return "gestionnaire-mode";
+ case "TRESORIER":
+ return "tresorier-mode";
+ case "MEMBER":
+ default:
+ return "member-mode";
+ }
+ }
+
+ public String getPermissionMessage(String action) {
+ return "Vous n'avez pas les permissions nécessaires pour " + action;
+ }
+
+ // Getters pour utilisation dans les expressions EL
+ public boolean isAuthenticated() {
+ return userSession != null && userSession.isAuthenticated();
+ }
+
+ public boolean isSuperAdmin() {
+ return hasRole("SUPER_ADMIN");
+ }
+
+ public boolean isAdmin() {
+ return hasRole("ADMIN");
+ }
+
+ public boolean isMember() {
+ return hasRole("MEMBER");
+ }
+
+ public boolean isGestionnaire() {
+ return hasAnyRole("GESTIONNAIRE_MEMBRE", "GESTIONNAIRE_EVENEMENT", "GESTIONNAIRE_AIDE", "GESTIONNAIRE_FINANCE");
+ }
+
+ public boolean isTresorier() {
+ return hasRole("TRESORIER");
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/security/TokenCleanupService.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/security/TokenCleanupService.java
new file mode 100644
index 0000000..9db1c3e
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/security/TokenCleanupService.java
@@ -0,0 +1,26 @@
+package dev.lions.unionflow.client.security;
+
+import io.quarkus.scheduler.Scheduled;
+import jakarta.enterprise.context.ApplicationScoped;
+import jakarta.inject.Inject;
+import java.util.logging.Logger;
+
+@ApplicationScoped
+public class TokenCleanupService {
+
+ private static final Logger LOGGER = Logger.getLogger(TokenCleanupService.class.getName());
+
+ @Inject
+ private TokenRefreshService tokenRefreshService;
+
+ @Scheduled(every = "10m")
+ public void cleanupExpiredTokens() {
+ try {
+ LOGGER.fine("Exécution du nettoyage des tokens expirés");
+ tokenRefreshService.cleanupExpiredTokens();
+ LOGGER.fine("Nettoyage des tokens terminé");
+ } catch (Exception e) {
+ LOGGER.warning("Erreur lors du nettoyage des tokens: " + e.getMessage());
+ }
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/security/TokenRefreshService.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/security/TokenRefreshService.java
new file mode 100644
index 0000000..a2274ed
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/security/TokenRefreshService.java
@@ -0,0 +1,150 @@
+package dev.lions.unionflow.client.security;
+
+import dev.lions.unionflow.client.dto.auth.LoginResponse;
+import dev.lions.unionflow.client.service.AuthenticationService;
+import jakarta.enterprise.context.ApplicationScoped;
+import jakarta.inject.Inject;
+import java.util.Map;
+import java.util.concurrent.ConcurrentHashMap;
+import java.util.logging.Logger;
+
+@ApplicationScoped
+public class TokenRefreshService {
+
+ private static final Logger LOGGER = Logger.getLogger(TokenRefreshService.class.getName());
+
+ @Inject
+ private AuthenticationService authService;
+
+ // Stockage des tokens au niveau application pour éviter les problèmes de contexte session
+ private final Map activeTokens = new ConcurrentHashMap<>();
+
+ private static class TokenInfo {
+ String accessToken;
+ String refreshToken;
+ long expirationTime;
+ String sessionId;
+
+ TokenInfo(String accessToken, String refreshToken, long expirationTime, String sessionId) {
+ this.accessToken = accessToken;
+ this.refreshToken = refreshToken;
+ this.expirationTime = expirationTime;
+ this.sessionId = sessionId;
+ }
+
+ boolean needsRefresh() {
+ // Rafraîchir 5 minutes avant l'expiration
+ long timeUntilExpiration = expirationTime - System.currentTimeMillis();
+ return timeUntilExpiration < 300000; // 5 minutes en millisecondes
+ }
+
+ boolean isExpired() {
+ return System.currentTimeMillis() > expirationTime;
+ }
+ }
+
+ public void registerToken(String sessionId, String accessToken, String refreshToken, long expiresIn) {
+ if (sessionId != null && accessToken != null) {
+ long expirationTime = System.currentTimeMillis() + (expiresIn * 1000);
+ activeTokens.put(sessionId, new TokenInfo(accessToken, refreshToken, expirationTime, sessionId));
+ LOGGER.info("Token enregistré pour la session: " + sessionId);
+ }
+ }
+
+ public void removeToken(String sessionId) {
+ if (sessionId != null) {
+ activeTokens.remove(sessionId);
+ LOGGER.info("Token supprimé pour la session: " + sessionId);
+ }
+ }
+
+ // Cette méthode n'est plus appelée par le scheduler pour éviter les problèmes de contexte
+ // Elle peut être appelée manuellement depuis un contexte avec session active
+ public void checkAndRefreshTokens(String sessionId) {
+ try {
+ TokenInfo tokenInfo = activeTokens.get(sessionId);
+
+ if (tokenInfo != null && tokenInfo.needsRefresh() && tokenInfo.refreshToken != null) {
+ LOGGER.info("Rafraîchissement du token JWT nécessaire pour session: " + sessionId);
+
+ LoginResponse refreshedResponse = authService.refreshToken(tokenInfo.refreshToken);
+
+ if (refreshedResponse != null) {
+ // Mettre à jour les tokens stockés
+ registerToken(sessionId,
+ refreshedResponse.getAccessToken(),
+ refreshedResponse.getRefreshToken(),
+ refreshedResponse.getExpiresIn());
+
+ LOGGER.info("Token JWT rafraîchi avec succès pour session: " + sessionId);
+ } else {
+ LOGGER.warning("Échec du rafraîchissement du token JWT pour session: " + sessionId);
+ handleTokenRefreshFailure(sessionId);
+ }
+ }
+ } catch (Exception e) {
+ LOGGER.severe("Erreur lors du rafraîchissement du token: " + e.getMessage());
+ handleTokenRefreshFailure(sessionId);
+ }
+ }
+
+ public boolean tryRefreshTokenNow(String sessionId) {
+ try {
+ TokenInfo tokenInfo = activeTokens.get(sessionId);
+
+ if (tokenInfo != null && tokenInfo.refreshToken != null) {
+ LoginResponse refreshedResponse = authService.refreshToken(tokenInfo.refreshToken);
+
+ if (refreshedResponse != null) {
+ registerToken(sessionId,
+ refreshedResponse.getAccessToken(),
+ refreshedResponse.getRefreshToken(),
+ refreshedResponse.getExpiresIn());
+
+ LOGGER.info("Token rafraîchi manuellement avec succès pour session: " + sessionId);
+ return true;
+ }
+ }
+ } catch (Exception e) {
+ LOGGER.warning("Échec du rafraîchissement manuel du token: " + e.getMessage());
+ }
+
+ return false;
+ }
+
+ private void handleTokenRefreshFailure(String sessionId) {
+ // En cas d'échec du rafraîchissement, supprimer le token
+ removeToken(sessionId);
+ LOGGER.info("Session expirée - token supprimé pour: " + sessionId);
+ }
+
+ public boolean isTokenExpired(String sessionId) {
+ TokenInfo tokenInfo = activeTokens.get(sessionId);
+ return tokenInfo == null || tokenInfo.isExpired();
+ }
+
+ public long getTimeUntilExpiration(String sessionId) {
+ TokenInfo tokenInfo = activeTokens.get(sessionId);
+ if (tokenInfo != null) {
+ long timeLeft = tokenInfo.expirationTime - System.currentTimeMillis();
+ return Math.max(0, timeLeft / 1000); // Retourner en secondes
+ }
+ return 0;
+ }
+
+ public String getAccessToken(String sessionId) {
+ TokenInfo tokenInfo = activeTokens.get(sessionId);
+ return tokenInfo != null ? tokenInfo.accessToken : null;
+ }
+
+ // Méthode pour nettoyer les tokens expirés périodiquement
+ public void cleanupExpiredTokens() {
+ activeTokens.entrySet().removeIf(entry -> {
+ boolean expired = entry.getValue().isExpired();
+ if (expired) {
+ LOGGER.info("Suppression du token expiré pour session: " + entry.getKey());
+ }
+ return expired;
+ });
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/service/AssociationService.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/service/AssociationService.java
new file mode 100644
index 0000000..a977a8e
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/service/AssociationService.java
@@ -0,0 +1,167 @@
+package dev.lions.unionflow.client.service;
+
+import dev.lions.unionflow.client.dto.AssociationDTO;
+import org.eclipse.microprofile.rest.client.inject.RegisterRestClient;
+import jakarta.ws.rs.*;
+import jakarta.ws.rs.core.MediaType;
+import java.util.List;
+
+@RegisterRestClient(configKey = "unionflow-api")
+@Path("/api/associations")
+@Consumes(MediaType.APPLICATION_JSON)
+@Produces(MediaType.APPLICATION_JSON)
+public interface AssociationService {
+
+ @GET
+ List listerToutes();
+
+ @GET
+ @Path("/{id}")
+ AssociationDTO obtenirParId(@PathParam("id") Long id);
+
+ @GET
+ @Path("/search")
+ List rechercher(
+ @QueryParam("nom") String nom,
+ @QueryParam("type") String type,
+ @QueryParam("statut") String statut,
+ @QueryParam("region") String region,
+ @QueryParam("ville") String ville,
+ @QueryParam("page") @DefaultValue("0") int page,
+ @QueryParam("size") @DefaultValue("20") int size
+ );
+
+ @GET
+ @Path("/actives")
+ List listerActives();
+
+ @GET
+ @Path("/type/{type}")
+ List listerParType(@PathParam("type") String type);
+
+ @GET
+ @Path("/region/{region}")
+ List listerParRegion(@PathParam("region") String region);
+
+ @POST
+ AssociationDTO creer(AssociationDTO association);
+
+ @PUT
+ @Path("/{id}")
+ AssociationDTO modifier(@PathParam("id") Long id, AssociationDTO association);
+
+ @DELETE
+ @Path("/{id}")
+ void supprimer(@PathParam("id") Long id);
+
+ @PUT
+ @Path("/{id}/activer")
+ AssociationDTO activer(@PathParam("id") Long id);
+
+ @PUT
+ @Path("/{id}/desactiver")
+ AssociationDTO desactiver(@PathParam("id") Long id);
+
+ @PUT
+ @Path("/{id}/suspendre")
+ AssociationDTO suspendre(@PathParam("id") Long id);
+
+ @PUT
+ @Path("/{id}/dissoudre")
+ AssociationDTO dissoudre(@PathParam("id") Long id);
+
+ @GET
+ @Path("/statistiques")
+ StatistiquesAssociationDTO obtenirStatistiques();
+
+ @GET
+ @Path("/{id}/membres/count")
+ Long compterMembres(@PathParam("id") Long id);
+
+ @GET
+ @Path("/{id}/performance")
+ PerformanceAssociationDTO obtenirPerformance(@PathParam("id") Long id);
+
+ // Classes DTO internes
+ class StatistiquesAssociationDTO {
+ public Long totalAssociations;
+ public Long associationsActives;
+ public Long associationsInactives;
+ public Long associationsSuspendues;
+ public Long associationsDissoutes;
+ public Long nouvellesAssociations30Jours;
+ public Double tauxActivite;
+ public java.util.Map repartitionParType;
+ public java.util.Map repartitionParRegion;
+
+ // Constructeurs
+ public StatistiquesAssociationDTO() {}
+
+ // Getters et setters
+ public Long getTotalAssociations() { return totalAssociations; }
+ public void setTotalAssociations(Long totalAssociations) { this.totalAssociations = totalAssociations; }
+
+ public Long getAssociationsActives() { return associationsActives; }
+ public void setAssociationsActives(Long associationsActives) { this.associationsActives = associationsActives; }
+
+ public Long getAssociationsInactives() { return associationsInactives; }
+ public void setAssociationsInactives(Long associationsInactives) { this.associationsInactives = associationsInactives; }
+
+ public Long getAssociationsSuspendues() { return associationsSuspendues; }
+ public void setAssociationsSuspendues(Long associationsSuspendues) { this.associationsSuspendues = associationsSuspendues; }
+
+ public Long getAssociationsDissoutes() { return associationsDissoutes; }
+ public void setAssociationsDissoutes(Long associationsDissoutes) { this.associationsDissoutes = associationsDissoutes; }
+
+ public Long getNouvellesAssociations30Jours() { return nouvellesAssociations30Jours; }
+ public void setNouvellesAssociations30Jours(Long nouvellesAssociations30Jours) { this.nouvellesAssociations30Jours = nouvellesAssociations30Jours; }
+
+ public Double getTauxActivite() { return tauxActivite; }
+ public void setTauxActivite(Double tauxActivite) { this.tauxActivite = tauxActivite; }
+
+ public java.util.Map getRepartitionParType() { return repartitionParType; }
+ public void setRepartitionParType(java.util.Map repartitionParType) { this.repartitionParType = repartitionParType; }
+
+ public java.util.Map getRepartitionParRegion() { return repartitionParRegion; }
+ public void setRepartitionParRegion(java.util.Map repartitionParRegion) { this.repartitionParRegion = repartitionParRegion; }
+ }
+
+ class PerformanceAssociationDTO {
+ public Long associationId;
+ public String nom;
+ public Integer scoreGlobal;
+ public Integer scoreMembres;
+ public Integer scoreActivites;
+ public Integer scoreFinances;
+ public String tendance;
+ public java.time.LocalDateTime derniereMiseAJour;
+
+ // Constructeurs
+ public PerformanceAssociationDTO() {}
+
+ // Getters et setters
+ public Long getAssociationId() { return associationId; }
+ public void setAssociationId(Long associationId) { this.associationId = associationId; }
+
+ public String getNom() { return nom; }
+ public void setNom(String nom) { this.nom = nom; }
+
+ public Integer getScoreGlobal() { return scoreGlobal; }
+ public void setScoreGlobal(Integer scoreGlobal) { this.scoreGlobal = scoreGlobal; }
+
+ public Integer getScoreMembres() { return scoreMembres; }
+ public void setScoreMembres(Integer scoreMembres) { this.scoreMembres = scoreMembres; }
+
+ public Integer getScoreActivites() { return scoreActivites; }
+ public void setScoreActivites(Integer scoreActivites) { this.scoreActivites = scoreActivites; }
+
+ public Integer getScoreFinances() { return scoreFinances; }
+ public void setScoreFinances(Integer scoreFinances) { this.scoreFinances = scoreFinances; }
+
+ public String getTendance() { return tendance; }
+ public void setTendance(String tendance) { this.tendance = tendance; }
+
+ public java.time.LocalDateTime getDerniereMiseAJour() { return derniereMiseAJour; }
+ public void setDerniereMiseAJour(java.time.LocalDateTime derniereMiseAJour) { this.derniereMiseAJour = derniereMiseAJour; }
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/service/AuthenticationService.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/service/AuthenticationService.java
new file mode 100644
index 0000000..f6e7e85
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/service/AuthenticationService.java
@@ -0,0 +1,170 @@
+package dev.lions.unionflow.client.service;
+
+import dev.lions.unionflow.client.dto.auth.LoginRequest;
+import dev.lions.unionflow.client.dto.auth.LoginResponse;
+import jakarta.enterprise.context.ApplicationScoped;
+import jakarta.ws.rs.client.Client;
+import jakarta.ws.rs.client.ClientBuilder;
+import jakarta.ws.rs.client.Entity;
+import jakarta.ws.rs.core.MediaType;
+import jakarta.ws.rs.core.Response;
+import org.eclipse.microprofile.config.inject.ConfigProperty;
+import java.util.logging.Logger;
+
+@ApplicationScoped
+public class AuthenticationService {
+
+ private static final Logger LOGGER = Logger.getLogger(AuthenticationService.class.getName());
+
+ @ConfigProperty(name = "unionflow.backend.url", defaultValue = "http://localhost:8080")
+ String backendUrl;
+
+ private final Client client;
+
+ public AuthenticationService() {
+ this.client = ClientBuilder.newClient();
+ }
+
+ public LoginResponse authenticate(LoginRequest loginRequest) {
+ try {
+ String endpoint = backendUrl + "/api/auth/login";
+
+ LOGGER.info("Tentative d'authentification vers: " + endpoint);
+
+ Response response = client.target(endpoint)
+ .request(MediaType.APPLICATION_JSON)
+ .post(Entity.entity(loginRequest, MediaType.APPLICATION_JSON));
+
+ if (response.getStatus() == 200) {
+ LoginResponse loginResponse = response.readEntity(LoginResponse.class);
+ LOGGER.info("Authentification réussie pour l'utilisateur: " + loginRequest.getUsername());
+ return loginResponse;
+ } else {
+ LOGGER.warning("Échec de l'authentification. Code de statut: " + response.getStatus());
+ throw new AuthenticationException("Nom d'utilisateur ou mot de passe incorrect");
+ }
+
+ } catch (Exception e) {
+ LOGGER.severe("Erreur lors de l'authentification: " + e.getMessage());
+
+ // Mode simulation pour le développement
+ if ("demo".equals(loginRequest.getUsername()) || isValidDemoCredentials(loginRequest)) {
+ return createDemoLoginResponse(loginRequest);
+ }
+
+ throw new AuthenticationException("Erreur de connexion au serveur d'authentification");
+ }
+ }
+
+ public LoginResponse refreshToken(String refreshToken) {
+ try {
+ String endpoint = backendUrl + "/api/auth/refresh";
+
+ Response response = client.target(endpoint)
+ .request(MediaType.APPLICATION_JSON)
+ .header("Authorization", "Bearer " + refreshToken)
+ .post(Entity.text(""));
+
+ if (response.getStatus() == 200) {
+ return response.readEntity(LoginResponse.class);
+ } else {
+ throw new AuthenticationException("Token de rafraîchissement invalide");
+ }
+
+ } catch (Exception e) {
+ LOGGER.severe("Erreur lors du rafraîchissement du token: " + e.getMessage());
+ throw new AuthenticationException("Erreur lors du rafraîchissement du token");
+ }
+ }
+
+ public void logout(String accessToken) {
+ try {
+ String endpoint = backendUrl + "/api/auth/logout";
+
+ client.target(endpoint)
+ .request()
+ .header("Authorization", "Bearer " + accessToken)
+ .post(Entity.text(""));
+
+ } catch (Exception e) {
+ LOGGER.warning("Erreur lors de la déconnexion: " + e.getMessage());
+ }
+ }
+
+ private boolean isValidDemoCredentials(LoginRequest request) {
+ return ("admin".equals(request.getUsername()) && "admin".equals(request.getPassword())) ||
+ ("superadmin".equals(request.getUsername()) && "admin".equals(request.getPassword())) ||
+ ("membre".equals(request.getUsername()) && "membre".equals(request.getPassword()));
+ }
+
+ private LoginResponse createDemoLoginResponse(LoginRequest request) {
+ LoginResponse.UserInfo userInfo = new LoginResponse.UserInfo();
+
+ switch (request.getUsername()) {
+ case "superadmin":
+ userInfo.setId(1L);
+ userInfo.setNom("Diallo");
+ userInfo.setPrenom("Amadou");
+ userInfo.setEmail("amadou.diallo@unionflow.sn");
+ userInfo.setUsername("superadmin");
+ userInfo.setTypeCompte("SUPER_ADMIN");
+ userInfo.setRoles(java.util.Arrays.asList("SUPER_ADMIN", "ADMIN"));
+ break;
+
+ case "admin":
+ userInfo.setId(2L);
+ userInfo.setNom("Traoré");
+ userInfo.setPrenom("Fatou");
+ userInfo.setEmail("fatou.traore@association-example.sn");
+ userInfo.setUsername("admin");
+ userInfo.setTypeCompte("ADMIN_ENTITE");
+ userInfo.setRoles(java.util.Arrays.asList("ADMIN_ENTITE"));
+
+ // Entité de démonstration
+ LoginResponse.EntiteInfo entite = new LoginResponse.EntiteInfo();
+ entite.setId(1L);
+ entite.setNom("Association des Jeunes Entrepreneurs");
+ entite.setType("Association");
+ entite.setPays("Sénégal");
+ entite.setVille("Dakar");
+ userInfo.setEntite(entite);
+ break;
+
+ default:
+ userInfo.setId(3L);
+ userInfo.setNom("Ndiaye");
+ userInfo.setPrenom("Moussa");
+ userInfo.setEmail("moussa.ndiaye@exemple.sn");
+ userInfo.setUsername("membre");
+ userInfo.setTypeCompte("MEMBRE");
+ userInfo.setRoles(java.util.Arrays.asList("MEMBRE"));
+
+ // Entité de démonstration
+ LoginResponse.EntiteInfo entiteMembre = new LoginResponse.EntiteInfo();
+ entiteMembre.setId(1L);
+ entiteMembre.setNom("Association des Jeunes Entrepreneurs");
+ entiteMembre.setType("Association");
+ entiteMembre.setPays("Sénégal");
+ entiteMembre.setVille("Dakar");
+ userInfo.setEntite(entiteMembre);
+ break;
+ }
+
+ return new LoginResponse(
+ "demo_access_token_" + System.currentTimeMillis(),
+ "demo_refresh_token_" + System.currentTimeMillis(),
+ 3600L, // 1 heure
+ userInfo
+ );
+ }
+
+ public static class AuthenticationException extends RuntimeException {
+ public AuthenticationException(String message) {
+ super(message);
+ }
+
+ public AuthenticationException(String message, Throwable cause) {
+ super(message, cause);
+ }
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/service/MembreService.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/service/MembreService.java
new file mode 100644
index 0000000..660b2ea
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/service/MembreService.java
@@ -0,0 +1,165 @@
+package dev.lions.unionflow.client.service;
+
+import dev.lions.unionflow.client.dto.MembreDTO;
+import org.eclipse.microprofile.rest.client.inject.RegisterRestClient;
+import jakarta.ws.rs.*;
+import jakarta.ws.rs.core.MediaType;
+import java.util.List;
+
+@RegisterRestClient(configKey = "unionflow-api")
+@Path("/api/membres")
+@Consumes(MediaType.APPLICATION_JSON)
+@Produces(MediaType.APPLICATION_JSON)
+public interface MembreService {
+
+ @GET
+ List listerTous();
+
+ @GET
+ @Path("/{id}")
+ MembreDTO obtenirParId(@PathParam("id") Long id);
+
+ @GET
+ @Path("/numero/{numeroMembre}")
+ MembreDTO obtenirParNumero(@PathParam("numeroMembre") String numeroMembre);
+
+ @GET
+ @Path("/search")
+ List rechercher(
+ @QueryParam("nom") String nom,
+ @QueryParam("prenom") String prenom,
+ @QueryParam("email") String email,
+ @QueryParam("telephone") String telephone,
+ @QueryParam("statut") String statut,
+ @QueryParam("associationId") Long associationId,
+ @QueryParam("page") @DefaultValue("0") int page,
+ @QueryParam("size") @DefaultValue("20") int size
+ );
+
+ @GET
+ @Path("/association/{associationId}")
+ List listerParAssociation(@PathParam("associationId") Long associationId);
+
+ @GET
+ @Path("/actifs")
+ List listerActifs();
+
+ @GET
+ @Path("/inactifs")
+ List listerInactifs();
+
+ @POST
+ MembreDTO creer(MembreDTO membre);
+
+ @PUT
+ @Path("/{id}")
+ MembreDTO modifier(@PathParam("id") Long id, MembreDTO membre);
+
+ @DELETE
+ @Path("/{id}")
+ void supprimer(@PathParam("id") Long id);
+
+ @PUT
+ @Path("/{id}/activer")
+ MembreDTO activer(@PathParam("id") Long id);
+
+ @PUT
+ @Path("/{id}/desactiver")
+ MembreDTO desactiver(@PathParam("id") Long id);
+
+ @PUT
+ @Path("/{id}/suspendre")
+ MembreDTO suspendre(@PathParam("id") Long id);
+
+ @PUT
+ @Path("/{id}/radier")
+ MembreDTO radier(@PathParam("id") Long id);
+
+ @GET
+ @Path("/statistiques")
+ StatistiquesMembreDTO obtenirStatistiques();
+
+ @GET
+ @Path("/export")
+ @Produces("application/vnd.openxmlformats-officedocument.spreadsheetml.sheet")
+ byte[] exporterExcel(
+ @QueryParam("format") @DefaultValue("EXCEL") String format,
+ @QueryParam("associationId") Long associationId,
+ @QueryParam("statut") String statut
+ );
+
+ @POST
+ @Path("/import")
+ @Consumes(MediaType.MULTIPART_FORM_DATA)
+ ResultatImportDTO importerDonnees(
+ @FormParam("file") java.io.InputStream fileInputStream,
+ @FormParam("associationId") Long associationId
+ );
+
+ // Classes DTO internes pour les réponses spécialisées
+ class StatistiquesMembreDTO {
+ public Long totalMembres;
+ public Long membresActifs;
+ public Long membresInactifs;
+ public Long membresSuspendus;
+ public Long membresRadies;
+ public Long nouveauxMembres30Jours;
+ public Double tauxActivite;
+ public Double tauxCroissance;
+
+ // Constructeurs
+ public StatistiquesMembreDTO() {}
+
+ // Getters et setters
+ public Long getTotalMembres() { return totalMembres; }
+ public void setTotalMembres(Long totalMembres) { this.totalMembres = totalMembres; }
+
+ public Long getMembresActifs() { return membresActifs; }
+ public void setMembresActifs(Long membresActifs) { this.membresActifs = membresActifs; }
+
+ public Long getMembresInactifs() { return membresInactifs; }
+ public void setMembresInactifs(Long membresInactifs) { this.membresInactifs = membresInactifs; }
+
+ public Long getMembresSuspendus() { return membresSuspendus; }
+ public void setMembresSuspendus(Long membresSuspendus) { this.membresSuspendus = membresSuspendus; }
+
+ public Long getMembresRadies() { return membresRadies; }
+ public void setMembresRadies(Long membresRadies) { this.membresRadies = membresRadies; }
+
+ public Long getNouveauxMembres30Jours() { return nouveauxMembres30Jours; }
+ public void setNouveauxMembres30Jours(Long nouveauxMembres30Jours) { this.nouveauxMembres30Jours = nouveauxMembres30Jours; }
+
+ public Double getTauxActivite() { return tauxActivite; }
+ public void setTauxActivite(Double tauxActivite) { this.tauxActivite = tauxActivite; }
+
+ public Double getTauxCroissance() { return tauxCroissance; }
+ public void setTauxCroissance(Double tauxCroissance) { this.tauxCroissance = tauxCroissance; }
+ }
+
+ class ResultatImportDTO {
+ public Integer totalLignes;
+ public Integer lignesTraitees;
+ public Integer lignesErreur;
+ public List erreurs;
+ public List membresImportes;
+
+ // Constructeurs
+ public ResultatImportDTO() {}
+
+ // Getters et setters
+ public Integer getTotalLignes() { return totalLignes; }
+ public void setTotalLignes(Integer totalLignes) { this.totalLignes = totalLignes; }
+
+ public Integer getLignesTraitees() { return lignesTraitees; }
+ public void setLignesTraitees(Integer lignesTraitees) { this.lignesTraitees = lignesTraitees; }
+
+ public Integer getLignesErreur() { return lignesErreur; }
+ public void setLignesErreur(Integer lignesErreur) { this.lignesErreur = lignesErreur; }
+
+ public List getErreurs() { return erreurs; }
+ public void setErreurs(List erreurs) { this.erreurs = erreurs; }
+
+ public List getMembresImportes() { return membresImportes; }
+ public void setMembresImportes(List membresImportes) { this.membresImportes = membresImportes; }
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/service/RestClientExceptionMapper.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/service/RestClientExceptionMapper.java
new file mode 100644
index 0000000..1d13117
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/service/RestClientExceptionMapper.java
@@ -0,0 +1,86 @@
+package dev.lions.unionflow.client.service;
+
+import jakarta.ws.rs.core.MultivaluedMap;
+import jakarta.ws.rs.core.Response;
+import org.eclipse.microprofile.rest.client.ext.ResponseExceptionMapper;
+
+import java.io.ByteArrayInputStream;
+import java.io.InputStream;
+
+public class RestClientExceptionMapper implements ResponseExceptionMapper {
+
+ @Override
+ public RuntimeException toThrowable(Response response) {
+ int status = response.getStatus();
+ String reasonPhrase = response.getStatusInfo().getReasonPhrase();
+
+ // Lire le corps de la réponse pour plus de détails
+ String body = "";
+ try {
+ if (response.hasEntity()) {
+ body = response.readEntity(String.class);
+ }
+ } catch (Exception e) {
+ body = "Impossible de lire le détail de l'erreur";
+ }
+
+ return switch (status) {
+ case 400 -> new BadRequestException("Requête invalide: " + body);
+ case 401 -> new UnauthorizedException("Non autorisé: " + reasonPhrase);
+ case 403 -> new ForbiddenException("Accès interdit: " + reasonPhrase);
+ case 404 -> new NotFoundException("Ressource non trouvée: " + reasonPhrase);
+ case 409 -> new ConflictException("Conflit: " + body);
+ case 422 -> new UnprocessableEntityException("Données non valides: " + body);
+ case 500 -> new InternalServerErrorException("Erreur serveur interne: " + body);
+ case 502 -> new BadGatewayException("Erreur de passerelle: " + reasonPhrase);
+ case 503 -> new ServiceUnavailableException("Service indisponible: " + reasonPhrase);
+ case 504 -> new GatewayTimeoutException("Timeout de passerelle: " + reasonPhrase);
+ default -> new UnknownHttpStatusException("Erreur HTTP " + status + ": " + reasonPhrase + (body.isEmpty() ? "" : " - " + body));
+ };
+ }
+
+ // Classes d'exception personnalisées
+ public static class BadRequestException extends RuntimeException {
+ public BadRequestException(String message) { super(message); }
+ }
+
+ public static class UnauthorizedException extends RuntimeException {
+ public UnauthorizedException(String message) { super(message); }
+ }
+
+ public static class ForbiddenException extends RuntimeException {
+ public ForbiddenException(String message) { super(message); }
+ }
+
+ public static class NotFoundException extends RuntimeException {
+ public NotFoundException(String message) { super(message); }
+ }
+
+ public static class ConflictException extends RuntimeException {
+ public ConflictException(String message) { super(message); }
+ }
+
+ public static class UnprocessableEntityException extends RuntimeException {
+ public UnprocessableEntityException(String message) { super(message); }
+ }
+
+ public static class InternalServerErrorException extends RuntimeException {
+ public InternalServerErrorException(String message) { super(message); }
+ }
+
+ public static class BadGatewayException extends RuntimeException {
+ public BadGatewayException(String message) { super(message); }
+ }
+
+ public static class ServiceUnavailableException extends RuntimeException {
+ public ServiceUnavailableException(String message) { super(message); }
+ }
+
+ public static class GatewayTimeoutException extends RuntimeException {
+ public GatewayTimeoutException(String message) { super(message); }
+ }
+
+ public static class UnknownHttpStatusException extends RuntimeException {
+ public UnknownHttpStatusException(String message) { super(message); }
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/service/ValidationService.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/service/ValidationService.java
new file mode 100644
index 0000000..ccf4816
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/service/ValidationService.java
@@ -0,0 +1,102 @@
+package dev.lions.unionflow.client.service;
+
+import jakarta.enterprise.context.ApplicationScoped;
+import jakarta.inject.Inject;
+import jakarta.validation.ConstraintViolation;
+import jakarta.validation.Validator;
+import java.util.ArrayList;
+import java.util.List;
+import java.util.Set;
+
+@ApplicationScoped
+public class ValidationService {
+
+ @Inject
+ Validator validator;
+
+ /**
+ * Valide un objet et retourne la liste des erreurs
+ */
+ public ValidationResult validate(T object) {
+ Set> violations = validator.validate(object);
+
+ ValidationResult result = new ValidationResult();
+ result.setValid(violations.isEmpty());
+
+ List messages = new ArrayList<>();
+ for (ConstraintViolation violation : violations) {
+ messages.add(violation.getPropertyPath() + ": " + violation.getMessage());
+ }
+ result.setErrorMessages(messages);
+
+ return result;
+ }
+
+ /**
+ * Valide une propriété spécifique d'un objet
+ */
+ public ValidationResult validateProperty(T object, String propertyName) {
+ Set> violations = validator.validateProperty(object, propertyName);
+
+ ValidationResult result = new ValidationResult();
+ result.setValid(violations.isEmpty());
+
+ List messages = new ArrayList<>();
+ for (ConstraintViolation violation : violations) {
+ messages.add(violation.getMessage());
+ }
+ result.setErrorMessages(messages);
+
+ return result;
+ }
+
+ /**
+ * Valide une valeur contre les contraintes d'une propriété
+ */
+ public ValidationResult validateValue(Class beanType, String propertyName, Object value) {
+ Set> violations = validator.validateValue(beanType, propertyName, value);
+
+ ValidationResult result = new ValidationResult();
+ result.setValid(violations.isEmpty());
+
+ List messages = new ArrayList<>();
+ for (ConstraintViolation violation : violations) {
+ messages.add(violation.getMessage());
+ }
+ result.setErrorMessages(messages);
+
+ return result;
+ }
+
+ /**
+ * Classe pour encapsuler le résultat de validation
+ */
+ public static class ValidationResult {
+ private boolean valid;
+ private List errorMessages = new ArrayList<>();
+
+ public boolean isValid() {
+ return valid;
+ }
+
+ public void setValid(boolean valid) {
+ this.valid = valid;
+ }
+
+ public List getErrorMessages() {
+ return errorMessages;
+ }
+
+ public void setErrorMessages(List errorMessages) {
+ this.errorMessages = errorMessages;
+ }
+
+ public String getFirstErrorMessage() {
+ return errorMessages.isEmpty() ? null : errorMessages.get(0);
+ }
+
+ public String getAllErrorMessages() {
+ return String.join(", ", errorMessages);
+ }
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/validation/MemberNumberValidator.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/validation/MemberNumberValidator.java
new file mode 100644
index 0000000..3d87d20
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/validation/MemberNumberValidator.java
@@ -0,0 +1,51 @@
+package dev.lions.unionflow.client.validation;
+
+import jakarta.validation.ConstraintValidator;
+import jakarta.validation.ConstraintValidatorContext;
+import java.util.regex.Pattern;
+
+public class MemberNumberValidator implements ConstraintValidator {
+
+ // Pattern pour numéro de membre: M + année + numéro séquentiel
+ private static final Pattern MEMBER_NUMBER_PATTERN = Pattern.compile("^M[0-9]{4}[0-9]{3,6}$");
+
+ @Override
+ public void initialize(ValidMemberNumber constraintAnnotation) {
+ // Initialisation si nécessaire
+ }
+
+ @Override
+ public boolean isValid(String memberNumber, ConstraintValidatorContext context) {
+ // Null ou vide = invalide pour un numéro de membre
+ if (memberNumber == null || memberNumber.trim().isEmpty()) {
+ return false;
+ }
+
+ // Nettoyer le numéro (supprimer espaces)
+ String cleanNumber = memberNumber.trim().toUpperCase();
+
+ // Vérifier le pattern
+ if (!MEMBER_NUMBER_PATTERN.matcher(cleanNumber).matches()) {
+ return false;
+ }
+
+ // Vérifier que l'année est raisonnable (entre 2020 et année actuelle + 1)
+ try {
+ String yearStr = cleanNumber.substring(1, 5);
+ int year = Integer.parseInt(yearStr);
+ int currentYear = java.time.Year.now().getValue();
+
+ if (year < 2020 || year > currentYear + 1) {
+ context.disableDefaultConstraintViolation();
+ context.buildConstraintViolationWithTemplate(
+ "L'année dans le numéro de membre doit être entre 2020 et " + (currentYear + 1)
+ ).addConstraintViolation();
+ return false;
+ }
+ } catch (NumberFormatException e) {
+ return false;
+ }
+
+ return true;
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/validation/PhoneNumberValidator.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/validation/PhoneNumberValidator.java
new file mode 100644
index 0000000..02db898
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/validation/PhoneNumberValidator.java
@@ -0,0 +1,46 @@
+package dev.lions.unionflow.client.validation;
+
+import jakarta.validation.ConstraintValidator;
+import jakarta.validation.ConstraintValidatorContext;
+import java.util.regex.Pattern;
+
+public class PhoneNumberValidator implements ConstraintValidator {
+
+ // Patterns pour différents formats de téléphone africains
+ private static final Pattern[] PHONE_PATTERNS = {
+ Pattern.compile("^(\\+225|225)?[0-9]{8}$"), // Côte d'Ivoire
+ Pattern.compile("^(\\+221|221)?[0-9]{9}$"), // Sénégal
+ Pattern.compile("^(\\+226|226)?[0-9]{8}$"), // Burkina Faso
+ Pattern.compile("^(\\+223|223)?[0-9]{8}$"), // Mali
+ Pattern.compile("^(\\+228|228)?[0-9]{8}$"), // Togo
+ Pattern.compile("^(\\+229|229)?[0-9]{8}$"), // Bénin
+ Pattern.compile("^(\\+233|233)?[0-9]{9}$"), // Ghana
+ Pattern.compile("^(\\+234|234)?[0-9]{10}$"), // Nigeria
+ Pattern.compile("^[0-9]{8,15}$") // Format générique
+ };
+
+ @Override
+ public void initialize(ValidPhoneNumber constraintAnnotation) {
+ // Initialisation si nécessaire
+ }
+
+ @Override
+ public boolean isValid(String phone, ConstraintValidatorContext context) {
+ // Null ou vide = valide (utiliser @NotBlank si obligatoire)
+ if (phone == null || phone.trim().isEmpty()) {
+ return true;
+ }
+
+ // Nettoyer le numéro (supprimer espaces, tirets, etc.)
+ String cleanPhone = phone.replaceAll("[\\s\\-\\(\\)\\.]", "");
+
+ // Vérifier contre tous les patterns
+ for (Pattern pattern : PHONE_PATTERNS) {
+ if (pattern.matcher(cleanPhone).matches()) {
+ return true;
+ }
+ }
+
+ return false;
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/validation/ValidMemberNumber.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/validation/ValidMemberNumber.java
new file mode 100644
index 0000000..8076baa
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/validation/ValidMemberNumber.java
@@ -0,0 +1,18 @@
+package dev.lions.unionflow.client.validation;
+
+import jakarta.validation.Constraint;
+import jakarta.validation.Payload;
+import java.lang.annotation.*;
+
+@Documented
+@Constraint(validatedBy = MemberNumberValidator.class)
+@Target({ElementType.FIELD, ElementType.METHOD, ElementType.PARAMETER})
+@Retention(RetentionPolicy.RUNTIME)
+public @interface ValidMemberNumber {
+
+ String message() default "Numéro de membre invalide. Format attendu: M + année + numéro (ex: M2024001)";
+
+ Class>[] groups() default {};
+
+ Class extends Payload>[] payload() default {};
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/validation/ValidPhoneNumber.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/validation/ValidPhoneNumber.java
new file mode 100644
index 0000000..488b14c
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/validation/ValidPhoneNumber.java
@@ -0,0 +1,18 @@
+package dev.lions.unionflow.client.validation;
+
+import jakarta.validation.Constraint;
+import jakarta.validation.Payload;
+import java.lang.annotation.*;
+
+@Documented
+@Constraint(validatedBy = PhoneNumberValidator.class)
+@Target({ElementType.FIELD, ElementType.METHOD, ElementType.PARAMETER})
+@Retention(RetentionPolicy.RUNTIME)
+public @interface ValidPhoneNumber {
+
+ String message() default "Numéro de téléphone invalide. Formats acceptés: +225XXXXXXXX, 0XXXXXXXXX, etc.";
+
+ Class>[] groups() default {};
+
+ Class extends Payload>[] payload() default {};
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/validation/ValidationGroups.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/validation/ValidationGroups.java
new file mode 100644
index 0000000..9231b72
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/validation/ValidationGroups.java
@@ -0,0 +1,47 @@
+package dev.lions.unionflow.client.validation;
+
+/**
+ * Groupes de validation pour différents cas d'usage dans UnionFlow
+ */
+public class ValidationGroups {
+
+ /**
+ * Validation pour la création d'un nouveau membre
+ */
+ public interface CreateMember {}
+
+ /**
+ * Validation pour la mise à jour d'un membre existant
+ */
+ public interface UpdateMember {}
+
+ /**
+ * Validation pour la création d'une association
+ */
+ public interface CreateAssociation {}
+
+ /**
+ * Validation pour la mise à jour d'une association
+ */
+ public interface UpdateAssociation {}
+
+ /**
+ * Validation pour l'inscription rapide (champs minimum requis)
+ */
+ public interface QuickRegistration {}
+
+ /**
+ * Validation pour l'inscription complète (tous les champs)
+ */
+ public interface FullRegistration {}
+
+ /**
+ * Validation pour l'importation en masse
+ */
+ public interface BulkImport {}
+
+ /**
+ * Validation pour les données administratives
+ */
+ public interface AdminData {}
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/AdminFormulaireBean.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/AdminFormulaireBean.java
new file mode 100644
index 0000000..f1abd3f
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/AdminFormulaireBean.java
@@ -0,0 +1,344 @@
+package dev.lions.unionflow.client.view;
+
+import dev.lions.unionflow.client.dto.FormulaireDTO;
+import dev.lions.unionflow.client.dto.SouscriptionDTO;
+import jakarta.enterprise.context.SessionScoped;
+import jakarta.inject.Named;
+import java.io.Serializable;
+import java.math.BigDecimal;
+import java.time.LocalDateTime;
+import java.util.ArrayList;
+import java.util.List;
+
+@Named("adminFormulaireBean")
+@SessionScoped
+public class AdminFormulaireBean implements Serializable {
+
+ private static final long serialVersionUID = 1L;
+
+ private List formulaires;
+ private FormulaireDTO formulaireSelectionne;
+ private FormulaireDTO nouveauFormulaire;
+ private boolean modeEdition = false;
+ private boolean modeCreation = false;
+
+ // Statistiques
+ private int totalSouscriptions = 0;
+ private BigDecimal revenusFormulaires = BigDecimal.ZERO;
+ private String formulairePlusPopulaire = "";
+
+ public AdminFormulaireBean() {
+ initializeData();
+ }
+
+ private void initializeData() {
+ formulaires = new ArrayList<>();
+
+ // Formulaire STARTER
+ FormulaireDTO starter = new FormulaireDTO();
+ starter.setId(1L);
+ starter.setNom("Starter");
+ starter.setDescription("Parfait pour les petites associations débutantes");
+ starter.setQuotaMaxMembres(100);
+ starter.setPrixMensuel(new BigDecimal("2000"));
+ starter.setPrixAnnuel(new BigDecimal("20000"));
+ starter.setCouleurTheme("bg-blue-500");
+ starter.setIconeFormulaire("pi-star");
+ starter.setActif(true);
+ starter.setGestionMembres(true);
+ starter.setGestionCotisations(true);
+ starter.setNotificationsEmail(true);
+ starter.setDateCreation(LocalDateTime.now().minusMonths(6));
+ starter.setCreePar("Super Admin");
+ formulaires.add(starter);
+
+ // Formulaire STANDARD
+ FormulaireDTO standard = new FormulaireDTO();
+ standard.setId(2L);
+ standard.setNom("Standard");
+ standard.setDescription("Idéal pour les associations en croissance");
+ standard.setQuotaMaxMembres(200);
+ standard.setPrixMensuel(new BigDecimal("3000"));
+ standard.setPrixAnnuel(new BigDecimal("30000"));
+ standard.setCouleurTheme("bg-green-500");
+ standard.setIconeFormulaire("pi-users");
+ standard.setActif(true);
+ standard.setRecommande(true);
+ standard.setGestionMembres(true);
+ standard.setGestionCotisations(true);
+ standard.setGestionEvenements(true);
+ standard.setGestionAides(true);
+ standard.setNotificationsEmail(true);
+ standard.setGestionDocuments(true);
+ standard.setDateCreation(LocalDateTime.now().minusMonths(6));
+ standard.setCreePar("Super Admin");
+ formulaires.add(standard);
+
+ // Formulaire PREMIUM
+ FormulaireDTO premium = new FormulaireDTO();
+ premium.setId(3L);
+ premium.setNom("Premium");
+ premium.setDescription("Solution complète pour les grandes organisations");
+ premium.setQuotaMaxMembres(500);
+ premium.setPrixMensuel(new BigDecimal("4000"));
+ premium.setPrixAnnuel(new BigDecimal("40000"));
+ premium.setCouleurTheme("bg-purple-500");
+ premium.setIconeFormulaire("pi-crown");
+ premium.setActif(true);
+ premium.setGestionMembres(true);
+ premium.setGestionCotisations(true);
+ premium.setGestionEvenements(true);
+ premium.setGestionAides(true);
+ premium.setRapportsAvances(true);
+ premium.setSupportPrioritaire(true);
+ premium.setSauvegardeAutomatique(true);
+ premium.setPersonnalisationAvancee(true);
+ premium.setIntegrationPaiement(true);
+ premium.setNotificationsEmail(true);
+ premium.setNotificationsSMS(true);
+ premium.setGestionDocuments(true);
+ premium.setDateCreation(LocalDateTime.now().minusMonths(6));
+ premium.setCreePar("Super Admin");
+ formulaires.add(premium);
+
+ // Formulaire CRISTAL - Pour les très grandes organisations
+ FormulaireDTO cristal = new FormulaireDTO();
+ cristal.setId(4L);
+ cristal.setNom("Cristal");
+ cristal.setDescription("Solution premium pour les fédérations et grandes entités");
+ cristal.setQuotaMaxMembres(2000);
+ cristal.setPrixMensuel(new BigDecimal("5000"));
+ cristal.setPrixAnnuel(new BigDecimal("50000"));
+ cristal.setCouleurTheme("bg-indigo-500");
+ cristal.setIconeFormulaire("pi-diamond");
+ cristal.setActif(true);
+ cristal.setGestionMembres(true);
+ cristal.setGestionCotisations(true);
+ cristal.setGestionEvenements(true);
+ cristal.setGestionAides(true);
+ cristal.setRapportsAvances(true);
+ cristal.setSupportPrioritaire(true);
+ cristal.setSauvegardeAutomatique(true);
+ cristal.setPersonnalisationAvancee(true);
+ cristal.setIntegrationPaiement(true);
+ cristal.setNotificationsEmail(true);
+ cristal.setNotificationsSMS(true);
+ cristal.setGestionDocuments(true);
+ cristal.setDateCreation(LocalDateTime.now().minusMonths(6));
+ cristal.setCreePar("Super Admin");
+ formulaires.add(cristal);
+
+ // Initialiser les statistiques
+ totalSouscriptions = 127; // Plus d'entités avec prix accessibles
+ revenusFormulaires = new BigDecimal("381000"); // 127 * 3000 (moyenne)
+ formulairePlusPopulaire = "Standard";
+ }
+
+ // Actions CRUD
+ public void nouveauFormulaire() {
+ nouveauFormulaire = new FormulaireDTO();
+ nouveauFormulaire.setActif(true);
+ nouveauFormulaire.setDeviseCode("XOF");
+ nouveauFormulaire.setGestionMembres(true);
+ nouveauFormulaire.setGestionCotisations(true);
+ modeCreation = true;
+ modeEdition = false;
+ }
+
+ public void editerFormulaire(FormulaireDTO formulaire) {
+ this.formulaireSelectionne = formulaire;
+ this.nouveauFormulaire = cloneFormulaire(formulaire);
+ modeEdition = true;
+ modeCreation = false;
+ }
+
+ public void sauvegarderFormulaire() {
+ if (modeCreation) {
+ // Générer un nouvel ID
+ Long nouvelId = formulaires.stream()
+ .mapToLong(FormulaireDTO::getId)
+ .max()
+ .orElse(0L) + 1;
+ nouveauFormulaire.setId(nouvelId);
+ nouveauFormulaire.setDateCreation(LocalDateTime.now());
+ nouveauFormulaire.setCreePar("Admin");
+
+ formulaires.add(nouveauFormulaire);
+
+ } else if (modeEdition) {
+ // Mettre à jour le formulaire existant
+ int index = formulaires.indexOf(formulaireSelectionne);
+ if (index >= 0) {
+ nouveauFormulaire.setDateMiseAJour(LocalDateTime.now());
+ nouveauFormulaire.setModifiePar("Admin");
+ formulaires.set(index, nouveauFormulaire);
+ }
+ }
+
+ annulerEdition();
+ }
+
+ public void supprimerFormulaire(FormulaireDTO formulaire) {
+ // Vérifier s'il y a des souscriptions actives
+ if (hasActiveSouscriptions(formulaire)) {
+ // Désactiver au lieu de supprimer
+ formulaire.setActif(false);
+ } else {
+ formulaires.remove(formulaire);
+ }
+ }
+
+ public void annulerEdition() {
+ modeCreation = false;
+ modeEdition = false;
+ formulaireSelectionne = null;
+ nouveauFormulaire = null;
+ }
+
+ public void dupliquerFormulaire(FormulaireDTO formulaire) {
+ FormulaireDTO copie = cloneFormulaire(formulaire);
+ copie.setId(null);
+ copie.setNom(formulaire.getNom() + " (Copie)");
+ copie.setDateCreation(LocalDateTime.now());
+ copie.setCreePar("Admin");
+
+ this.nouveauFormulaire = copie;
+ modeCreation = true;
+ modeEdition = false;
+ }
+
+ public void activerDesactiverFormulaire(FormulaireDTO formulaire) {
+ formulaire.setActif(!formulaire.isActif());
+ formulaire.setDateMiseAJour(LocalDateTime.now());
+ formulaire.setModifiePar("Admin");
+ }
+
+ // Méthodes utilitaires
+ private FormulaireDTO cloneFormulaire(FormulaireDTO original) {
+ FormulaireDTO copie = new FormulaireDTO();
+ copie.setId(original.getId());
+ copie.setNom(original.getNom());
+ copie.setDescription(original.getDescription());
+ copie.setQuotaMaxMembres(original.getQuotaMaxMembres());
+ copie.setPrixMensuel(original.getPrixMensuel());
+ copie.setPrixAnnuel(original.getPrixAnnuel());
+ copie.setDeviseCode(original.getDeviseCode());
+ copie.setActif(original.isActif());
+ copie.setRecommande(original.isRecommande());
+ copie.setCouleurTheme(original.getCouleurTheme());
+ copie.setIconeFormulaire(original.getIconeFormulaire());
+
+ // Fonctionnalités
+ copie.setGestionMembres(original.isGestionMembres());
+ copie.setGestionCotisations(original.isGestionCotisations());
+ copie.setGestionEvenements(original.isGestionEvenements());
+ copie.setGestionAides(original.isGestionAides());
+ copie.setRapportsAvances(original.isRapportsAvances());
+ copie.setSupportPrioritaire(original.isSupportPrioritaire());
+ copie.setSauvegardeAutomatique(original.isSauvegardeAutomatique());
+ copie.setPersonnalisationAvancee(original.isPersonnalisationAvancee());
+ copie.setIntegrationPaiement(original.isIntegrationPaiement());
+ copie.setNotificationsEmail(original.isNotificationsEmail());
+ copie.setNotificationsSMS(original.isNotificationsSMS());
+ copie.setGestionDocuments(original.isGestionDocuments());
+
+ // Métadonnées
+ copie.setDateCreation(original.getDateCreation());
+ copie.setDateMiseAJour(original.getDateMiseAJour());
+ copie.setCreePar(original.getCreePar());
+ copie.setModifiePar(original.getModifiePar());
+
+ return copie;
+ }
+
+ private boolean hasActiveSouscriptions(FormulaireDTO formulaire) {
+ // Simulation - vérifier s'il y a des souscriptions actives
+ return "Standard".equals(formulaire.getNom()) || "Premium".equals(formulaire.getNom());
+ }
+
+ public boolean canDeleteFormulaire(FormulaireDTO formulaire) {
+ return !hasActiveSouscriptions(formulaire);
+ }
+
+ public String getStatutFormulaire(FormulaireDTO formulaire) {
+ if (formulaire.isActif()) {
+ return hasActiveSouscriptions(formulaire) ? "Actif avec souscriptions" : "Actif";
+ }
+ return "Inactif";
+ }
+
+ public String getCouleurStatut(FormulaireDTO formulaire) {
+ if (formulaire.isActif()) {
+ return hasActiveSouscriptions(formulaire) ? "text-green-600" : "text-blue-600";
+ }
+ return "text-gray-600";
+ }
+
+ // Validation
+ public boolean isFormulaireValide() {
+ if (nouveauFormulaire == null) return false;
+
+ return nouveauFormulaire.getNom() != null && !nouveauFormulaire.getNom().trim().isEmpty() &&
+ nouveauFormulaire.getQuotaMaxMembres() != null && nouveauFormulaire.getQuotaMaxMembres() > 0 &&
+ nouveauFormulaire.getPrixMensuel() != null && nouveauFormulaire.getPrixMensuel().compareTo(BigDecimal.ZERO) > 0 &&
+ nouveauFormulaire.getPrixAnnuel() != null && nouveauFormulaire.getPrixAnnuel().compareTo(BigDecimal.ZERO) > 0;
+ }
+
+ // Listes pour les sélections
+ public List getCouleursTheme() {
+ List couleurs = new ArrayList<>();
+ couleurs.add("bg-blue-500");
+ couleurs.add("bg-green-500");
+ couleurs.add("bg-purple-500");
+ couleurs.add("bg-indigo-500");
+ couleurs.add("bg-red-500");
+ couleurs.add("bg-orange-500");
+ couleurs.add("bg-yellow-500");
+ couleurs.add("bg-teal-500");
+ couleurs.add("bg-pink-500");
+ return couleurs;
+ }
+
+ public List getIconesFormulaire() {
+ List icones = new ArrayList<>();
+ icones.add("pi-star");
+ icones.add("pi-users");
+ icones.add("pi-crown");
+ icones.add("pi-building");
+ icones.add("pi-heart");
+ icones.add("pi-shield");
+ icones.add("pi-trophy");
+ icones.add("pi-diamond");
+ icones.add("pi-thumbs-up");
+ return icones;
+ }
+
+ // Getters et Setters
+ public List getFormulaires() { return formulaires; }
+ public void setFormulaires(List formulaires) { this.formulaires = formulaires; }
+
+ public FormulaireDTO getFormulaireSelectionne() { return formulaireSelectionne; }
+ public void setFormulaireSelectionne(FormulaireDTO formulaireSelectionne) { this.formulaireSelectionne = formulaireSelectionne; }
+
+ public FormulaireDTO getNouveauFormulaire() { return nouveauFormulaire; }
+ public void setNouveauFormulaire(FormulaireDTO nouveauFormulaire) { this.nouveauFormulaire = nouveauFormulaire; }
+
+ public boolean isModeEdition() { return modeEdition; }
+ public void setModeEdition(boolean modeEdition) { this.modeEdition = modeEdition; }
+
+ public boolean isModeCreation() { return modeCreation; }
+ public void setModeCreation(boolean modeCreation) { this.modeCreation = modeCreation; }
+
+ public int getTotalSouscriptions() { return totalSouscriptions; }
+ public void setTotalSouscriptions(int totalSouscriptions) { this.totalSouscriptions = totalSouscriptions; }
+
+ public BigDecimal getRevenusFormulaires() { return revenusFormulaires; }
+ public void setRevenusFormulaires(BigDecimal revenusFormulaires) { this.revenusFormulaires = revenusFormulaires; }
+
+ public String getFormulairePlusPopulaire() { return formulairePlusPopulaire; }
+ public void setFormulairePlusPopulaire(String formulairePlusPopulaire) { this.formulairePlusPopulaire = formulairePlusPopulaire; }
+
+ public String getRevenusFormulairesFormat() {
+ return String.format("%,.0f XOF", revenusFormulaires);
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/AuditBean.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/AuditBean.java
new file mode 100644
index 0000000..c1395cd
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/AuditBean.java
@@ -0,0 +1,454 @@
+package dev.lions.unionflow.client.view;
+
+import jakarta.enterprise.context.SessionScoped;
+import jakarta.inject.Named;
+import java.io.Serializable;
+import java.time.LocalDateTime;
+import java.time.format.DateTimeFormatter;
+import java.util.*;
+import java.util.stream.Collectors;
+
+@Named("auditBean")
+@SessionScoped
+public class AuditBean implements Serializable {
+
+ private static final long serialVersionUID = 1L;
+
+ // Filtres
+ private Date dateDebut;
+ private Date dateFin;
+ private String typeAction = "";
+ private String severite = "";
+ private String utilisateur = "";
+ private String module = "";
+ private String ipAddress = "";
+
+ // Données
+ private List evenements;
+ private EvenementAudit evenementSelectionne;
+
+ // Export
+ private String formatExport = "EXCEL";
+ private boolean inclureFiltresExport = true;
+
+ public AuditBean() {
+ initialiserEvenements();
+ // Initialiser les dates à aujourd'hui - 7 jours
+ Calendar cal = Calendar.getInstance();
+ dateFin = cal.getTime();
+ cal.add(Calendar.DAY_OF_MONTH, -7);
+ dateDebut = cal.getTime();
+ }
+
+ private void initialiserEvenements() {
+ evenements = new ArrayList<>();
+ LocalDateTime now = LocalDateTime.now();
+
+ // Événements de connexion
+ evenements.add(new EvenementAudit(
+ now.minusMinutes(15), "CONNEXION", "SUCCESS", "Marie Dupont", "ADMIN_ORG", "AUTH",
+ "Connexion réussie", "Connexion via interface web", "192.168.1.105",
+ "Mozilla/5.0 (Windows NT 10.0; Win64; x64)", "SESSION_123456"));
+
+ evenements.add(new EvenementAudit(
+ now.minusMinutes(32), "CONNEXION", "ERROR", "Jean Martin", "MEMBRE", "AUTH",
+ "Tentative de connexion échouée", "Mot de passe incorrect (3e tentative)", "192.168.1.87",
+ "Mozilla/5.0 (Macintosh; Intel Mac OS X)", "SESSION_789012"));
+
+ // Événements de gestion des membres
+ evenements.add(new EvenementAudit(
+ now.minusHours(1), "CREATION", "SUCCESS", "Marie Dupont", "ADMIN_ORG", "MEMBRES",
+ "Création d'un nouveau membre", "Membre: Paul Durand (ID: MBR_2024_001)", "192.168.1.105",
+ "Mozilla/5.0 (Windows NT 10.0; Win64; x64)", "SESSION_123456"));
+
+ evenements.add(new EvenementAudit(
+ now.minusHours(2), "MODIFICATION", "SUCCESS", "Sophie Bernard", "SECRETAIRE", "MEMBRES",
+ "Modification profil membre", "Mise à jour adresse email: paul.durand@email.com", "192.168.1.92",
+ "Mozilla/5.0 (iPhone; CPU iPhone OS)", "SESSION_345678"));
+
+ // Événements de cotisations
+ evenements.add(new EvenementAudit(
+ now.minusHours(3), "CREATION", "SUCCESS", "Pierre Legrand", "COMPTABLE", "COTISATIONS",
+ "Enregistrement paiement cotisation", "Cotisation 2024 - Membre: Marie Petit - 50€", "192.168.1.78",
+ "Mozilla/5.0 (Windows NT 10.0; Win64; x64)", "SESSION_901234"));
+
+ // Événements d'export
+ evenements.add(new EvenementAudit(
+ now.minusHours(4), "EXPORT", "SUCCESS", "Marie Dupont", "ADMIN_ORG", "RAPPORTS",
+ "Export liste des membres", "Format Excel - 156 membres exportés", "192.168.1.105",
+ "Mozilla/5.0 (Windows NT 10.0; Win64; x64)", "SESSION_123456"));
+
+ // Événements de configuration
+ evenements.add(new EvenementAudit(
+ now.minusHours(6), "CONFIGURATION", "WARNING", "Admin Système", "SUPER_ADMIN", "CONFIG",
+ "Modification paramètres sécurité", "Durée de session modifiée: 30min → 60min", "192.168.1.1",
+ "Mozilla/5.0 (Linux; Ubuntu)", "SESSION_ADMIN001"));
+
+ // Événements suspects
+ evenements.add(new EvenementAudit(
+ now.minusHours(8), "CONNEXION", "CRITICAL", "Utilisateur Inconnu", "N/A", "AUTH",
+ "Tentative de connexion suspecte", "Multiples tentatives depuis IP externe", "203.45.67.89",
+ "Bot/1.0", "SESSION_UNKNOWN"));
+
+ evenements.add(new EvenementAudit(
+ now.minusHours(12), "CONSULTATION", "ERROR", "Test User", "MEMBRE", "DOCUMENTS",
+ "Accès non autorisé", "Tentative d'accès au document confidentiel DOC_2024_005", "192.168.1.199",
+ "Mozilla/5.0 (Android)", "SESSION_567890"));
+
+ // Événements de suppression
+ evenements.add(new EvenementAudit(
+ now.minusHours(24), "SUPPRESSION", "WARNING", "Marie Dupont", "ADMIN_ORG", "EVENTS",
+ "Suppression événement", "Événement: Assemblée Générale 2023 supprimé", "192.168.1.105",
+ "Mozilla/5.0 (Windows NT 10.0; Win64; x64)", "SESSION_123456"));
+
+ // Plus d'événements pour la pagination
+ for (int i = 0; i < 50; i++) {
+ LocalDateTime date = now.minusHours(i + 1).minusMinutes(new Random().nextInt(60));
+ String[] users = {"Marie Dupont", "Jean Martin", "Pierre Legrand", "Sophie Bernard", "Paul Durand"};
+ String[] actions = {"CONSULTATION", "MODIFICATION", "CONNEXION", "DECONNEXION"};
+ String[] modules = {"MEMBRES", "COTISATIONS", "EVENTS", "DOCUMENTS"};
+ String[] ips = {"192.168.1.105", "192.168.1.87", "192.168.1.92", "192.168.1.78"};
+
+ String user = users[i % users.length];
+ String action = actions[i % actions.length];
+ String module = modules[i % modules.length];
+ String ip = ips[i % ips.length];
+ String severite = i % 10 == 0 ? "WARNING" : "SUCCESS";
+
+ evenements.add(new EvenementAudit(
+ date, action, severite, user, "MEMBRE", module,
+ "Action automatique " + (i + 1), "Détails de l'action " + (i + 1), ip,
+ "Mozilla/5.0 (Auto)", "SESSION_AUTO_" + i));
+ }
+
+ // Trier par date décroissante
+ evenements.sort((e1, e2) -> e2.getDateHeure().compareTo(e1.getDateHeure()));
+ }
+
+ // Getters pour KPIs
+ public int getTotalEvenements() {
+ return evenements.size();
+ }
+
+ public long getConnexionsReussies() {
+ return evenements.stream()
+ .filter(e -> "CONNEXION".equals(e.getTypeAction()) && "SUCCESS".equals(e.getSeverite()))
+ .filter(e -> e.getDateHeure().isAfter(LocalDateTime.now().toLocalDate().atStartOfDay()))
+ .count();
+ }
+
+ public long getTentativesEchouees() {
+ return evenements.stream()
+ .filter(e -> "CONNEXION".equals(e.getTypeAction()) && !"SUCCESS".equals(e.getSeverite()))
+ .filter(e -> e.getDateHeure().isAfter(LocalDateTime.now().minusWeeks(1)))
+ .count();
+ }
+
+ public long getAlertesSecurite() {
+ return evenements.stream()
+ .filter(e -> "CRITICAL".equals(e.getSeverite()) || "ERROR".equals(e.getSeverite()))
+ .count();
+ }
+
+ // Filtrage
+ public List getEvenementsFiltres() {
+ return evenements.stream()
+ .filter(this::correspondAuxFiltres)
+ .collect(Collectors.toList());
+ }
+
+ private boolean correspondAuxFiltres(EvenementAudit event) {
+ // Filtre par dates
+ if (dateDebut != null && event.getDateHeure().isBefore(convertToLocalDateTime(dateDebut))) {
+ return false;
+ }
+ if (dateFin != null && event.getDateHeure().isAfter(convertToLocalDateTime(dateFin).plusDays(1))) {
+ return false;
+ }
+
+ // Filtre par type d'action
+ if (!typeAction.isEmpty() && !typeAction.equals(event.getTypeAction())) {
+ return false;
+ }
+
+ // Filtre par sévérité
+ if (!severite.isEmpty() && !severite.equals(event.getSeverite())) {
+ return false;
+ }
+
+ // Filtre par utilisateur
+ if (!utilisateur.isEmpty() && !event.getUtilisateur().toLowerCase().contains(utilisateur.toLowerCase())) {
+ return false;
+ }
+
+ // Filtre par module
+ if (!module.isEmpty() && !module.equals(event.getModule())) {
+ return false;
+ }
+
+ // Filtre par IP
+ if (!ipAddress.isEmpty() && !event.getIpAddress().contains(ipAddress)) {
+ return false;
+ }
+
+ return true;
+ }
+
+ private LocalDateTime convertToLocalDateTime(Date date) {
+ return LocalDateTime.ofInstant(date.toInstant(), java.time.ZoneId.systemDefault());
+ }
+
+ // Actions
+ public void rechercher() {
+ // La recherche se fait automatiquement via le filtrage
+ }
+
+ public void reinitialiserFiltres() {
+ Calendar cal = Calendar.getInstance();
+ dateFin = cal.getTime();
+ cal.add(Calendar.DAY_OF_MONTH, -7);
+ dateDebut = cal.getTime();
+
+ typeAction = "";
+ severite = "";
+ utilisateur = "";
+ module = "";
+ ipAddress = "";
+ }
+
+ public void voirDetails(EvenementAudit event) {
+ this.evenementSelectionne = event;
+ }
+
+ public void signalerEvenement(EvenementAudit event) {
+ // Logique pour signaler un événement comme suspect
+ }
+
+ public void exporter() {
+ // Logique d'export selon le format sélectionné
+ }
+
+ // Getters et Setters
+ public Date getDateDebut() { return dateDebut; }
+ public void setDateDebut(Date dateDebut) { this.dateDebut = dateDebut; }
+
+ public Date getDateFin() { return dateFin; }
+ public void setDateFin(Date dateFin) { this.dateFin = dateFin; }
+
+ public String getTypeAction() { return typeAction; }
+ public void setTypeAction(String typeAction) { this.typeAction = typeAction; }
+
+ public String getSeverite() { return severite; }
+ public void setSeverite(String severite) { this.severite = severite; }
+
+ public String getUtilisateur() { return utilisateur; }
+ public void setUtilisateur(String utilisateur) { this.utilisateur = utilisateur; }
+
+ public String getModule() { return module; }
+ public void setModule(String module) { this.module = module; }
+
+ public String getIpAddress() { return ipAddress; }
+ public void setIpAddress(String ipAddress) { this.ipAddress = ipAddress; }
+
+ public EvenementAudit getEvenementSelectionne() { return evenementSelectionne; }
+ public void setEvenementSelectionne(EvenementAudit evenementSelectionne) { this.evenementSelectionne = evenementSelectionne; }
+
+ public String getFormatExport() { return formatExport; }
+ public void setFormatExport(String formatExport) { this.formatExport = formatExport; }
+
+ public boolean isInclurefiltresExport() { return inclureFiltresExport; }
+ public void setInclurefiltresExport(boolean inclureFiltresExport) { this.inclureFiltresExport = inclureFiltresExport; }
+
+ // Classe interne EvenementAudit
+ public static class EvenementAudit implements Serializable {
+ private LocalDateTime dateHeure;
+ 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;
+
+ public EvenementAudit(LocalDateTime dateHeure, String typeAction, String severite,
+ String utilisateur, String role, String module, String description,
+ String details, String ipAddress, String userAgent, String sessionId) {
+ this.dateHeure = dateHeure;
+ this.typeAction = typeAction;
+ this.severite = severite;
+ this.utilisateur = utilisateur;
+ this.role = role;
+ this.module = module;
+ this.description = description;
+ this.details = details;
+ this.ipAddress = ipAddress;
+ this.userAgent = userAgent;
+ this.sessionId = sessionId;
+ }
+
+ // Propriétés calculées pour l'affichage
+ public String getDateFormatee() {
+ return dateHeure.format(DateTimeFormatter.ofPattern("dd/MM/yyyy"));
+ }
+
+ public String getHeureFormatee() {
+ return dateHeure.format(DateTimeFormatter.ofPattern("HH:mm:ss"));
+ }
+
+ public String getDateHeureComplete() {
+ return dateHeure.format(DateTimeFormatter.ofPattern("dd/MM/yyyy HH:mm:ss"));
+ }
+
+ public String getSeveriteLibelle() {
+ switch (severite) {
+ case "SUCCESS": return "Succès";
+ case "INFO": return "Info";
+ case "WARNING": return "Attention";
+ case "ERROR": return "Erreur";
+ case "CRITICAL": return "Critique";
+ default: return severite;
+ }
+ }
+
+ public String getSeveriteSeverity() {
+ switch (severite) {
+ case "SUCCESS": return "success";
+ case "INFO": return "info";
+ case "WARNING": return "warning";
+ case "ERROR": return "danger";
+ case "CRITICAL": return "danger";
+ default: return "secondary";
+ }
+ }
+
+ public String getSeveriteIcon() {
+ switch (severite) {
+ case "SUCCESS": return "pi pi-check";
+ case "INFO": return "pi pi-info";
+ case "WARNING": return "pi pi-exclamation-triangle";
+ case "ERROR": return "pi pi-times";
+ case "CRITICAL": return "pi pi-ban";
+ default: return "pi pi-circle";
+ }
+ }
+
+ public String getActionIcon() {
+ switch (typeAction) {
+ case "CONNEXION": return "pi pi-sign-in";
+ case "DECONNEXION": return "pi pi-sign-out";
+ case "CREATION": return "pi pi-plus";
+ case "MODIFICATION": return "pi pi-pencil";
+ case "SUPPRESSION": return "pi pi-trash";
+ case "CONSULTATION": return "pi pi-eye";
+ case "EXPORT": return "pi pi-download";
+ case "CONFIGURATION": return "pi pi-cog";
+ default: return "pi pi-circle";
+ }
+ }
+
+ public String getActionColor() {
+ switch (typeAction) {
+ case "CONNEXION": return "#28a745";
+ case "DECONNEXION": return "#6c757d";
+ case "CREATION": return "#007bff";
+ case "MODIFICATION": return "#ffc107";
+ case "SUPPRESSION": return "#dc3545";
+ case "CONSULTATION": return "#17a2b8";
+ case "EXPORT": return "#6f42c1";
+ case "CONFIGURATION": return "#fd7e14";
+ default: return "#6c757d";
+ }
+ }
+
+ public String getModuleLibelle() {
+ switch (module) {
+ case "AUTH": return "Authentification";
+ case "MEMBRES": return "Membres";
+ case "COTISATIONS": return "Cotisations";
+ case "EVENTS": return "Événements";
+ case "DOCUMENTS": return "Documents";
+ case "CONFIG": return "Configuration";
+ case "RAPPORTS": return "Rapports";
+ default: return module;
+ }
+ }
+
+ public String getAction() {
+ switch (typeAction) {
+ case "CONNEXION": return "Connexion";
+ case "DECONNEXION": return "Déconnexion";
+ case "CREATION": return "Création";
+ case "MODIFICATION": return "Modification";
+ case "SUPPRESSION": return "Suppression";
+ case "CONSULTATION": return "Consultation";
+ case "EXPORT": return "Export";
+ case "CONFIGURATION": return "Configuration";
+ default: return typeAction;
+ }
+ }
+
+ public String getDescriptionComplete() {
+ return description + (details != null && !details.isEmpty() ? "\n\nDétails: " + details : "");
+ }
+
+ public String getUserAgentComplet() {
+ return userAgent;
+ }
+
+ public String getDonneesAvant() {
+ // Simulation de données avant modification
+ if ("MODIFICATION".equals(typeAction)) {
+ return "{\n \"nom\": \"Ancien Nom\",\n \"email\": \"ancien@email.com\",\n \"statut\": \"INACTIF\"\n}";
+ }
+ return null;
+ }
+
+ public String getDonneesApres() {
+ // Simulation de données après modification
+ if ("MODIFICATION".equals(typeAction)) {
+ return "{\n \"nom\": \"Nouveau Nom\",\n \"email\": \"nouveau@email.com\",\n \"statut\": \"ACTIF\"\n}";
+ }
+ return null;
+ }
+
+ // Getters et Setters
+ public LocalDateTime getDateHeure() { return dateHeure; }
+ public void setDateHeure(LocalDateTime dateHeure) { this.dateHeure = dateHeure; }
+
+ public String getTypeAction() { return typeAction; }
+ public void setTypeAction(String typeAction) { this.typeAction = typeAction; }
+
+ public String getSeverite() { return severite; }
+ public void setSeverite(String severite) { this.severite = severite; }
+
+ public String getUtilisateur() { return utilisateur; }
+ public void setUtilisateur(String utilisateur) { this.utilisateur = utilisateur; }
+
+ public String getRole() { return role; }
+ public void setRole(String role) { this.role = role; }
+
+ public String getModule() { return module; }
+ public void setModule(String module) { this.module = module; }
+
+ public String getDescription() { return description; }
+ public void setDescription(String description) { this.description = description; }
+
+ public String getDetails() { return details; }
+ public void setDetails(String details) { this.details = details; }
+
+ public String getIpAddress() { return ipAddress; }
+ public void setIpAddress(String ipAddress) { this.ipAddress = ipAddress; }
+
+ public String getUserAgent() {
+ return userAgent != null && userAgent.length() > 20 ?
+ userAgent.substring(0, 20) + "..." : userAgent;
+ }
+ public void setUserAgent(String userAgent) { this.userAgent = userAgent; }
+
+ public String getSessionId() { return sessionId; }
+ public void setSessionId(String sessionId) { this.sessionId = sessionId; }
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/ConfigurationBean.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/ConfigurationBean.java
new file mode 100644
index 0000000..cbb012c
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/ConfigurationBean.java
@@ -0,0 +1,730 @@
+package dev.lions.unionflow.client.view;
+
+import jakarta.enterprise.context.SessionScoped;
+import jakarta.inject.Named;
+import jakarta.annotation.PostConstruct;
+import java.io.Serializable;
+import java.time.LocalDateTime;
+import java.time.LocalTime;
+import java.time.format.DateTimeFormatter;
+
+@Named("configurationBean")
+@SessionScoped
+public class ConfigurationBean implements Serializable {
+
+ private static final long serialVersionUID = 1L;
+
+ private ConfigurationGenerale general;
+ private ConfigurationSecurite securite;
+ private ConfigurationEmail email;
+ private ConfigurationPaiements paiements;
+ private ConfigurationSysteme système;
+
+ // Propriétés pour la page système
+ private String nomApplication = "UnionFlow";
+ private String versionSysteme = "2.0.1";
+ private String environnement = "PROD";
+ private String timezone = "WAT";
+ private String langueDefaut = "fr";
+ private String deviseDefaut = "XOF";
+ private String urlBaseApplication = "https://unionflow.app";
+ private String formatDate = "dd/MM/yyyy";
+ private String organisationPrincipale = "Lions Clubs Afrique de l'Ouest";
+
+ // Configuration BDD enrichie
+ private String typeBDD = "postgresql";
+ private String serveurBDD = "localhost";
+ private Integer portBDD = 5432;
+ private String nomBDD = "unionflow";
+ private String utilisateurBDD = "unionflow_user";
+ private String motDePasseBDD = "";
+ private Integer taillePoolConnexions = 20;
+ private Boolean sslActifBDD = true;
+
+ // Configuration Email enrichie
+ private String serveurSMTP = "smtp.gmail.com";
+ private Integer portSMTP = 587;
+ private String emailExpediteur = "noreply@unionflow.app";
+ private String nomExpediteur = "UnionFlow Notifications";
+ private Boolean authentificationSMTP = true;
+ private String utilisateurSMTP = "";
+ private String motDePasseSMTP = "";
+ private Boolean tlsActive = true;
+ private Integer limiteTauxEmail = 500;
+
+ // Configuration Sécurité enrichie
+ private Integer timeoutSession = 30;
+ private Integer tentativesMaxConnexion = 5;
+ private Boolean forcerChangementMotDePasse = true;
+ private Boolean authentification2FA = true;
+ private Boolean journaliserEvenementsSecurite = true;
+ private String complexiteMotDePasse = "MEDIUM";
+ private Integer dureeValiditeMotDePasse = 90;
+ private Integer retentionLogs = 365;
+ private Boolean chiffrementBDD = true;
+
+ // Propriétés d'état système
+ private String tempsActivite = "99.8%";
+ private Integer utilisateursConnectes = 247;
+ private Integer memoireUtilisee = 68;
+ private String memoireTotal = "16";
+ private String derniereSauvegarde = "02:00";
+
+ // Monitoring avancé
+ private Integer cpuUtilisation = 45;
+ private Float disqueDisponible = 127.5f;
+ private Integer connexionsBDDActives = 15;
+ private Integer queueEmailsEnAttente = 23;
+ private Integer logsErreurs24h = 8;
+ private Integer sessionsActives = 127;
+
+ // Configuration avancée
+ private Boolean modeMaintenance = false;
+ private String frequenceSauvegarde = "DAILY";
+ private Integer retentionSauvegardes = 30;
+ private String emailAlertes = "admin@unionflow.app";
+ private Boolean alertesCPU = true;
+ private Boolean alertesMemoire = true;
+ private Boolean alertesDisque = true;
+
+ @PostConstruct
+ public void init() {
+ initializeGeneral();
+ initializeSecurite();
+ initializeEmail();
+ initializePaiements();
+ initializeSysteme();
+ calculerMetriquesSysteme();
+ }
+
+ private void calculerMetriquesSysteme() {
+ // Simulation des métriques système réelles pour UnionFlow
+ cpuUtilisation = (int) (Math.random() * 30) + 40; // 40-70%
+ memoireUtilisee = (int) (Math.random() * 20) + 60; // 60-80%
+ disqueDisponible = (float) (Math.random() * 50) + 100; // 100-150 GB
+ connexionsBDDActives = (int) (Math.random() * 10) + 10; // 10-20
+ queueEmailsEnAttente = (int) (Math.random() * 50) + 10; // 10-60
+ logsErreurs24h = (int) (Math.random() * 20) + 5; // 5-25
+ sessionsActives = utilisateursConnectes; // Basé sur utilisateurs connectés
+
+ // Optimisé pour la stratégie volume (127 organisations, 247 utilisateurs)
+ utilisateursConnectes = 247;
+ sessionsActives = 127; // Une session par organisation active
+ }
+
+ private void initializeGeneral() {
+ general = new ConfigurationGenerale();
+ general.setNomOrganisation("Organisation Centrale");
+ general.setSigleOrganisation("ORG-001");
+ general.setSiteWeb("https://unionflow.app");
+ general.setEmailContact("contact@unionflow.app");
+ general.setLangueDefaut("fr");
+ general.setDevise("XOF");
+ general.setFuseauHoraire("GMT");
+ general.setModeMaintenanceActif(false);
+ }
+
+ private void initializeSecurite() {
+ securite = new ConfigurationSecurite();
+ securite.setLongueurMinMotPasse(8);
+ securite.setExigerMajuscules(true);
+ securite.setExigerChiffres(true);
+ securite.setExigerCaracteresSpeciaux(false);
+ securite.setExpirationMotPasse(90);
+ securite.setTentativesConnexionMax(5);
+ securite.setDureeBlocage(15);
+ securite.setTimeoutSession(60);
+ securite.setDoubleFacteurObligatoire(false);
+ securite.setJournalisationAvancee(true);
+ }
+
+ private void initializeEmail() {
+ email = new ConfigurationEmail();
+ email.setServeurSMTP("smtp.gmail.com");
+ email.setPortSMTP(587);
+ email.setUtilisateurSMTP("noreply@unionflow.app");
+ email.setMotPasseSMTP("**********");
+ email.setUtiliserSSL(true);
+ email.setEmailExpediteur("noreply@unionflow.app");
+ email.setNomExpediteur("UnionFlow Platform");
+ email.setNotifierNouveauMembre(true);
+ email.setNotifierEvenements(true);
+ email.setRappelCotisations(true);
+ }
+
+ private void initializePaiements() {
+ paiements = new ConfigurationPaiements();
+ paiements.setWaveActif(true);
+ paiements.setWaveApiKey("**********");
+ paiements.setWaveSecretKey("**********");
+ paiements.setWaveEnvironnement("sandbox");
+ paiements.setEspècesActif(true);
+ paiements.setChèqueActif(true);
+ paiements.setVirementActif(true);
+ paiements.setIbanOrganisation("CI05 CI01 2345 6789 0123 4567 89");
+ paiements.setFraisPaiement(2.5);
+ }
+
+ private void initializeSysteme() {
+ système = new ConfigurationSysteme();
+ système.setCacheActivé(true);
+ système.setDureeCacheMinutes(30);
+ système.setTailleLotTraitement(100);
+ système.setNiveauLog("INFO");
+ système.setRetentionLogJours(30);
+ système.setMétriquesActivées(true);
+ système.setAlertesSystemeActivées(true);
+ }
+
+ // Actions générales
+ public void sauvegarderTout() {
+ System.out.println("Configuration complète sauvegardée à " + LocalDateTime.now().format(DateTimeFormatter.ofPattern("dd/MM/yyyy HH:mm:ss")));
+ }
+
+ public void reinitialiser() {
+ init();
+ System.out.println("Configuration réinitialisée aux valeurs par défaut");
+ }
+
+ public void exporterConfiguration() {
+ System.out.println("Export de la configuration généré");
+ }
+
+ // Actions par section
+ public void sauvegarderGeneral() {
+ System.out.println("Configuration générale sauvegardée");
+ }
+
+ public void sauvegarderSecurite() {
+ System.out.println("Configuration sécurité sauvegardée");
+ }
+
+ public void sauvegarderEmail() {
+ System.out.println("Configuration email sauvegardée");
+ }
+
+ // Actions pour la page système
+ public void sauvegarderConfiguration() {
+ System.out.println("Configuration système sauvegardée");
+ }
+
+ public void restaurerDefauts() {
+ nomApplication = "UnionFlow";
+ versionSysteme = "1.0.0";
+ environnement = "DEV";
+ System.out.println("Configuration système restaurée aux valeurs par défaut");
+ }
+
+ public void testerConnexionBDD() {
+ System.out.println("Test de connexion BDD: " + typeBDD + "://" + serveurBDD + ":" + portBDD + "/" + nomBDD);
+ // TODO: Implémenter le test réel
+ }
+
+ public void testerEmail() {
+ System.out.println("Test d'envoi d'email via " + serveurSMTP + ":" + portSMTP);
+ // TODO: Implémenter le test réel
+ System.out.println("Test email envoyé avec succès");
+ }
+
+ public void forcerSauvegarde() {
+ System.out.println("Sauvegarde forcée du système");
+ derniereSauvegarde = LocalDateTime.now().format(DateTimeFormatter.ofPattern("HH:mm"));
+ // TODO: Déclencher une sauvegarde immédiate
+ }
+
+ public void redemarrerServices() {
+ System.out.println("Redémarrage des services système en cours...");
+ // TODO: Redémarrer les services critiques
+ }
+
+ public void sauvegarderPaiements() {
+ System.out.println("Configuration paiements sauvegardée");
+ }
+
+ public void sauvegarderSysteme() {
+ System.out.println("Configuration système sauvegardée");
+ }
+
+ // Actions système
+ public void viderCache() {
+ System.out.println("Cache vidé avec succès");
+ }
+
+ public void optimiserBaseDonnees() {
+ System.out.println("Optimisation de la base de données en cours...");
+ }
+
+ public void sauvegarderBaseDonnees() {
+ System.out.println("Sauvegarde de la base de données initiée");
+ }
+
+ public String voirLogsSysteme() {
+ return "/pages/super-admin/logs?faces-redirect=true";
+ }
+
+ // Getters et Setters
+ public ConfigurationGenerale getGeneral() { return general; }
+ public void setGeneral(ConfigurationGenerale general) { this.general = general; }
+
+ public ConfigurationSecurite getSecurite() { return securite; }
+ public void setSecurite(ConfigurationSecurite securite) { this.securite = securite; }
+
+ public ConfigurationEmail getEmail() { return email; }
+ public void setEmail(ConfigurationEmail email) { this.email = email; }
+
+ public ConfigurationPaiements getPaiements() { return paiements; }
+ public void setPaiements(ConfigurationPaiements paiements) { this.paiements = paiements; }
+
+ public ConfigurationSysteme getSystème() { return système; }
+ public void setSystème(ConfigurationSysteme système) { this.système = système; }
+
+ // Classes internes pour la configuration
+ public static class ConfigurationGenerale {
+ private String nomOrganisation;
+ private String sigleOrganisation;
+ private String siteWeb;
+ private String emailContact;
+ private String langueDefaut;
+ private String devise;
+ private String fuseauHoraire;
+ private boolean modeMaintenanceActif;
+
+ // Getters et setters
+ public String getNomOrganisation() { return nomOrganisation; }
+ public void setNomOrganisation(String nomOrganisation) { this.nomOrganisation = nomOrganisation; }
+
+ public String getSigleOrganisation() { return sigleOrganisation; }
+ public void setSigleOrganisation(String sigleOrganisation) { this.sigleOrganisation = sigleOrganisation; }
+
+ public String getSiteWeb() { return siteWeb; }
+ public void setSiteWeb(String siteWeb) { this.siteWeb = siteWeb; }
+
+ public String getEmailContact() { return emailContact; }
+ public void setEmailContact(String emailContact) { this.emailContact = emailContact; }
+
+ public String getLangueDefaut() { return langueDefaut; }
+ public void setLangueDefaut(String langueDefaut) { this.langueDefaut = langueDefaut; }
+
+ public String getDevise() { return devise; }
+ public void setDevise(String devise) { this.devise = devise; }
+
+ public String getFuseauHoraire() { return fuseauHoraire; }
+ public void setFuseauHoraire(String fuseauHoraire) { this.fuseauHoraire = fuseauHoraire; }
+
+ public boolean isModeMaintenanceActif() { return modeMaintenanceActif; }
+ public void setModeMaintenanceActif(boolean modeMaintenanceActif) { this.modeMaintenanceActif = modeMaintenanceActif; }
+ }
+
+ public static class ConfigurationSecurite {
+ private int longueurMinMotPasse;
+ private boolean exigerMajuscules;
+ private boolean exigerChiffres;
+ private boolean exigerCaracteresSpeciaux;
+ private int expirationMotPasse;
+ private int tentativesConnexionMax;
+ private int dureeBlocage;
+ private int timeoutSession;
+ private boolean doubleFacteurObligatoire;
+ private boolean journalisationAvancee;
+
+ // Getters et setters
+ public int getLongueurMinMotPasse() { return longueurMinMotPasse; }
+ public void setLongueurMinMotPasse(int longueurMinMotPasse) { this.longueurMinMotPasse = longueurMinMotPasse; }
+
+ public boolean isExigerMajuscules() { return exigerMajuscules; }
+ public void setExigerMajuscules(boolean exigerMajuscules) { this.exigerMajuscules = exigerMajuscules; }
+
+ public boolean isExigerChiffres() { return exigerChiffres; }
+ public void setExigerChiffres(boolean exigerChiffres) { this.exigerChiffres = exigerChiffres; }
+
+ public boolean isExigerCaracteresSpeciaux() { return exigerCaracteresSpeciaux; }
+ public void setExigerCaracteresSpeciaux(boolean exigerCaracteresSpeciaux) { this.exigerCaracteresSpeciaux = exigerCaracteresSpeciaux; }
+
+ public int getExpirationMotPasse() { return expirationMotPasse; }
+ public void setExpirationMotPasse(int expirationMotPasse) { this.expirationMotPasse = expirationMotPasse; }
+
+ public int getTentativesConnexionMax() { return tentativesConnexionMax; }
+ public void setTentativesConnexionMax(int tentativesConnexionMax) { this.tentativesConnexionMax = tentativesConnexionMax; }
+
+ public int getDureeBlocage() { return dureeBlocage; }
+ public void setDureeBlocage(int dureeBlocage) { this.dureeBlocage = dureeBlocage; }
+
+ public int getTimeoutSession() { return timeoutSession; }
+ public void setTimeoutSession(int timeoutSession) { this.timeoutSession = timeoutSession; }
+
+ public boolean isDoubleFacteurObligatoire() { return doubleFacteurObligatoire; }
+ public void setDoubleFacteurObligatoire(boolean doubleFacteurObligatoire) { this.doubleFacteurObligatoire = doubleFacteurObligatoire; }
+
+ public boolean isJournalisationAvancee() { return journalisationAvancee; }
+ public void setJournalisationAvancee(boolean journalisationAvancee) { this.journalisationAvancee = journalisationAvancee; }
+ }
+
+ public static class ConfigurationEmail {
+ private String serveurSMTP;
+ private int portSMTP;
+ private String utilisateurSMTP;
+ private String motPasseSMTP;
+ private boolean utiliserSSL;
+ private String emailExpediteur;
+ private String nomExpediteur;
+ private boolean notifierNouveauMembre;
+ private boolean notifierEvenements;
+ private boolean rappelCotisations;
+
+ // Getters et setters
+ public String getServeurSMTP() { return serveurSMTP; }
+ public void setServeurSMTP(String serveurSMTP) { this.serveurSMTP = serveurSMTP; }
+
+ public int getPortSMTP() { return portSMTP; }
+ public void setPortSMTP(int portSMTP) { this.portSMTP = portSMTP; }
+
+ public String getUtilisateurSMTP() { return utilisateurSMTP; }
+ public void setUtilisateurSMTP(String utilisateurSMTP) { this.utilisateurSMTP = utilisateurSMTP; }
+
+ public String getMotPasseSMTP() { return motPasseSMTP; }
+ public void setMotPasseSMTP(String motPasseSMTP) { this.motPasseSMTP = motPasseSMTP; }
+
+ public boolean isUtiliserSSL() { return utiliserSSL; }
+ public void setUtiliserSSL(boolean utiliserSSL) { this.utiliserSSL = utiliserSSL; }
+
+ public String getEmailExpediteur() { return emailExpediteur; }
+ public void setEmailExpediteur(String emailExpediteur) { this.emailExpediteur = emailExpediteur; }
+
+ public String getNomExpediteur() { return nomExpediteur; }
+ public void setNomExpediteur(String nomExpediteur) { this.nomExpediteur = nomExpediteur; }
+
+ public boolean isNotifierNouveauMembre() { return notifierNouveauMembre; }
+ public void setNotifierNouveauMembre(boolean notifierNouveauMembre) { this.notifierNouveauMembre = notifierNouveauMembre; }
+
+ public boolean isNotifierEvenements() { return notifierEvenements; }
+ public void setNotifierEvenements(boolean notifierEvenements) { this.notifierEvenements = notifierEvenements; }
+
+ public boolean isRappelCotisations() { return rappelCotisations; }
+ public void setRappelCotisations(boolean rappelCotisations) { this.rappelCotisations = rappelCotisations; }
+ }
+
+ public static class ConfigurationPaiements {
+ private boolean waveActif;
+ private String waveApiKey;
+ private String waveSecretKey;
+ private String waveEnvironnement;
+ private boolean espècesActif;
+ private boolean chèqueActif;
+ private boolean virementActif;
+ private String ibanOrganisation;
+ private double fraisPaiement;
+
+ // Getters et setters
+ public boolean isWaveActif() { return waveActif; }
+ public void setWaveActif(boolean waveActif) { this.waveActif = waveActif; }
+
+ public String getWaveApiKey() { return waveApiKey; }
+ public void setWaveApiKey(String waveApiKey) { this.waveApiKey = waveApiKey; }
+
+ public String getWaveSecretKey() { return waveSecretKey; }
+ public void setWaveSecretKey(String waveSecretKey) { this.waveSecretKey = waveSecretKey; }
+
+ public String getWaveEnvironnement() { return waveEnvironnement; }
+ public void setWaveEnvironnement(String waveEnvironnement) { this.waveEnvironnement = waveEnvironnement; }
+
+ public boolean isEspècesActif() { return espècesActif; }
+ public void setEspècesActif(boolean espècesActif) { this.espècesActif = espècesActif; }
+
+ public boolean isChèqueActif() { return chèqueActif; }
+ public void setChèqueActif(boolean chèqueActif) { this.chèqueActif = chèqueActif; }
+
+ public boolean isVirementActif() { return virementActif; }
+ public void setVirementActif(boolean virementActif) { this.virementActif = virementActif; }
+
+ public String getIbanOrganisation() { return ibanOrganisation; }
+ public void setIbanOrganisation(String ibanOrganisation) { this.ibanOrganisation = ibanOrganisation; }
+
+ public double getFraisPaiement() { return fraisPaiement; }
+ public void setFraisPaiement(double fraisPaiement) { this.fraisPaiement = fraisPaiement; }
+ }
+
+ // Getters et setters pour les propriétés système
+ public String getNomApplication() { return nomApplication; }
+ public void setNomApplication(String nomApplication) { this.nomApplication = nomApplication; }
+
+ public String getVersionSysteme() { return versionSysteme; }
+ public void setVersionSysteme(String versionSysteme) { this.versionSysteme = versionSysteme; }
+
+ public String getEnvironnement() { return environnement; }
+ public void setEnvironnement(String environnement) { this.environnement = environnement; }
+
+ public String getTimezone() { return timezone; }
+ public void setTimezone(String timezone) { this.timezone = timezone; }
+
+ public String getLangueDefaut() { return langueDefaut; }
+ public void setLangueDefaut(String langueDefaut) { this.langueDefaut = langueDefaut; }
+
+ public String getTypeBDD() { return typeBDD; }
+ public void setTypeBDD(String typeBDD) { this.typeBDD = typeBDD; }
+
+ public String getServeurBDD() { return serveurBDD; }
+ public void setServeurBDD(String serveurBDD) { this.serveurBDD = serveurBDD; }
+
+ public Integer getPortBDD() { return portBDD; }
+ public void setPortBDD(Integer portBDD) { this.portBDD = portBDD; }
+
+ public String getNomBDD() { return nomBDD; }
+ public void setNomBDD(String nomBDD) { this.nomBDD = nomBDD; }
+
+ public String getServeurSMTP() { return serveurSMTP; }
+ public void setServeurSMTP(String serveurSMTP) { this.serveurSMTP = serveurSMTP; }
+
+ public Integer getPortSMTP() { return portSMTP; }
+ public void setPortSMTP(Integer portSMTP) { this.portSMTP = portSMTP; }
+
+ public String getEmailExpediteur() { return emailExpediteur; }
+ public void setEmailExpediteur(String emailExpediteur) { this.emailExpediteur = emailExpediteur; }
+
+ public Boolean getAuthentificationSMTP() { return authentificationSMTP; }
+ public void setAuthentificationSMTP(Boolean authentificationSMTP) { this.authentificationSMTP = authentificationSMTP; }
+
+ public Boolean getTlsActive() { return tlsActive; }
+ public void setTlsActive(Boolean tlsActive) { this.tlsActive = tlsActive; }
+
+ public Integer getTimeoutSession() { return timeoutSession; }
+ public void setTimeoutSession(Integer timeoutSession) { this.timeoutSession = timeoutSession; }
+
+ public Integer getTentativesMaxConnexion() { return tentativesMaxConnexion; }
+ public void setTentativesMaxConnexion(Integer tentativesMaxConnexion) { this.tentativesMaxConnexion = tentativesMaxConnexion; }
+
+ public Boolean getForcerChangementMotDePasse() { return forcerChangementMotDePasse; }
+ public void setForcerChangementMotDePasse(Boolean forcerChangementMotDePasse) { this.forcerChangementMotDePasse = forcerChangementMotDePasse; }
+
+ public Boolean getAuthentification2FA() { return authentification2FA; }
+ public void setAuthentification2FA(Boolean authentification2FA) { this.authentification2FA = authentification2FA; }
+
+ public Boolean getJournaliserEvenementsSecurite() { return journaliserEvenementsSecurite; }
+ public void setJournaliserEvenementsSecurite(Boolean journaliserEvenementsSecurite) { this.journaliserEvenementsSecurite = journaliserEvenementsSecurite; }
+
+ public String getTempsActivite() { return tempsActivite; }
+ public void setTempsActivite(String tempsActivite) { this.tempsActivite = tempsActivite; }
+
+ public Integer getUtilisateursConnectes() { return utilisateursConnectes; }
+ public void setUtilisateursConnectes(Integer utilisateursConnectes) { this.utilisateursConnectes = utilisateursConnectes; }
+
+ public Integer getMemoireUtilisee() { return memoireUtilisee; }
+ public void setMemoireUtilisee(Integer memoireUtilisee) { this.memoireUtilisee = memoireUtilisee; }
+
+ public String getMemoireTotal() { return memoireTotal; }
+ public void setMemoireTotal(String memoireTotal) { this.memoireTotal = memoireTotal; }
+
+ public String getDerniereSauvegarde() { return derniereSauvegarde; }
+ public void setDerniereSauvegarde(String derniereSauvegarde) { this.derniereSauvegarde = derniereSauvegarde; }
+
+ // Nouveaux getters/setters pour configuration enrichie
+ public String getDeviseDefaut() { return deviseDefaut; }
+ public void setDeviseDefaut(String deviseDefaut) { this.deviseDefaut = deviseDefaut; }
+
+ public String getUrlBaseApplication() { return urlBaseApplication; }
+ public void setUrlBaseApplication(String urlBaseApplication) { this.urlBaseApplication = urlBaseApplication; }
+
+ public String getFormatDate() { return formatDate; }
+ public void setFormatDate(String formatDate) { this.formatDate = formatDate; }
+
+ public String getOrganisationPrincipale() { return organisationPrincipale; }
+ public void setOrganisationPrincipale(String organisationPrincipale) { this.organisationPrincipale = organisationPrincipale; }
+
+ public String getUtilisateurBDD() { return utilisateurBDD; }
+ public void setUtilisateurBDD(String utilisateurBDD) { this.utilisateurBDD = utilisateurBDD; }
+
+ public String getMotDePasseBDD() { return motDePasseBDD; }
+ public void setMotDePasseBDD(String motDePasseBDD) { this.motDePasseBDD = motDePasseBDD; }
+
+ public Integer getTaillePoolConnexions() { return taillePoolConnexions; }
+ public void setTaillePoolConnexions(Integer taillePoolConnexions) { this.taillePoolConnexions = taillePoolConnexions; }
+
+ public Boolean getSslActifBDD() { return sslActifBDD; }
+ public void setSslActifBDD(Boolean sslActifBDD) { this.sslActifBDD = sslActifBDD; }
+
+ public String getNomExpediteur() { return nomExpediteur; }
+ public void setNomExpediteur(String nomExpediteur) { this.nomExpediteur = nomExpediteur; }
+
+ public String getUtilisateurSMTP() { return utilisateurSMTP; }
+ public void setUtilisateurSMTP(String utilisateurSMTP) { this.utilisateurSMTP = utilisateurSMTP; }
+
+ public String getMotDePasseSMTP() { return motDePasseSMTP; }
+ public void setMotDePasseSMTP(String motDePasseSMTP) { this.motDePasseSMTP = motDePasseSMTP; }
+
+ public Integer getLimiteTauxEmail() { return limiteTauxEmail; }
+ public void setLimiteTauxEmail(Integer limiteTauxEmail) { this.limiteTauxEmail = limiteTauxEmail; }
+
+ public String getComplexiteMotDePasse() { return complexiteMotDePasse; }
+ public void setComplexiteMotDePasse(String complexiteMotDePasse) { this.complexiteMotDePasse = complexiteMotDePasse; }
+
+ public Integer getDureeValiditeMotDePasse() { return dureeValiditeMotDePasse; }
+ public void setDureeValiditeMotDePasse(Integer dureeValiditeMotDePasse) { this.dureeValiditeMotDePasse = dureeValiditeMotDePasse; }
+
+ public Integer getRetentionLogs() { return retentionLogs; }
+ public void setRetentionLogs(Integer retentionLogs) { this.retentionLogs = retentionLogs; }
+
+ public Boolean getChiffrementBDD() { return chiffrementBDD; }
+ public void setChiffrementBDD(Boolean chiffrementBDD) { this.chiffrementBDD = chiffrementBDD; }
+
+ public Integer getCpuUtilisation() { return cpuUtilisation; }
+ public void setCpuUtilisation(Integer cpuUtilisation) { this.cpuUtilisation = cpuUtilisation; }
+
+ public Float getDisqueDisponible() { return disqueDisponible; }
+ public void setDisqueDisponible(Float disqueDisponible) { this.disqueDisponible = disqueDisponible; }
+
+ public Integer getConnexionsBDDActives() { return connexionsBDDActives; }
+ public void setConnexionsBDDActives(Integer connexionsBDDActives) { this.connexionsBDDActives = connexionsBDDActives; }
+
+ public Integer getQueueEmailsEnAttente() { return queueEmailsEnAttente; }
+ public void setQueueEmailsEnAttente(Integer queueEmailsEnAttente) { this.queueEmailsEnAttente = queueEmailsEnAttente; }
+
+ public Integer getLogsErreurs24h() { return logsErreurs24h; }
+ public void setLogsErreurs24h(Integer logsErreurs24h) { this.logsErreurs24h = logsErreurs24h; }
+
+ public Integer getSessionsActives() { return sessionsActives; }
+ public void setSessionsActives(Integer sessionsActives) { this.sessionsActives = sessionsActives; }
+
+ public Boolean getModeMaintenance() { return modeMaintenance; }
+ public void setModeMaintenance(Boolean modeMaintenance) { this.modeMaintenance = modeMaintenance; }
+
+ public String getFrequenceSauvegarde() { return frequenceSauvegarde; }
+ public void setFrequenceSauvegarde(String frequenceSauvegarde) { this.frequenceSauvegarde = frequenceSauvegarde; }
+
+ public Integer getRetentionSauvegardes() { return retentionSauvegardes; }
+ public void setRetentionSauvegardes(Integer retentionSauvegardes) { this.retentionSauvegardes = retentionSauvegardes; }
+
+ public String getEmailAlertes() { return emailAlertes; }
+ public void setEmailAlertes(String emailAlertes) { this.emailAlertes = emailAlertes; }
+
+ public Boolean getAlertesCPU() { return alertesCPU; }
+ public void setAlertesCPU(Boolean alertesCPU) { this.alertesCPU = alertesCPU; }
+
+ public Boolean getAlertesMemoire() { return alertesMemoire; }
+ public void setAlertesMemoire(Boolean alertesMemoire) { this.alertesMemoire = alertesMemoire; }
+
+ public Boolean getAlertesDisque() { return alertesDisque; }
+ public void setAlertesDisque(Boolean alertesDisque) { this.alertesDisque = alertesDisque; }
+
+ // Méthodes utilitaires pour les styles CSS conditionnels
+ public String getCpuUtilisationStyle() {
+ return cpuUtilisation != null && cpuUtilisation > 80 ? "text-red-500" : "text-green-500";
+ }
+
+ public String getDisqueDisponibleStyle() {
+ return disqueDisponible != null && disqueDisponible < 10 ? "text-red-500" : "text-blue-500";
+ }
+
+ public String getQueueEmailsStyle() {
+ return queueEmailsEnAttente != null && queueEmailsEnAttente > 100 ? "text-orange-500" : "text-green-500";
+ }
+
+ public String getLogsErreursStyle() {
+ return logsErreurs24h != null && logsErreurs24h > 50 ? "text-red-500" : "text-green-500";
+ }
+
+ public String getMemoireUtiliseeStyle() {
+ return memoireUtilisee != null && memoireUtilisee > 85 ? "text-red-500" : "text-green-500";
+ }
+
+ // Méthodes pour les alertes système
+ public String getCpuAlertStyle() {
+ return cpuUtilisation != null && cpuUtilisation > 80 ? "bg-red-100" : "bg-green-100";
+ }
+
+ public String getCpuAlertIcon() {
+ return cpuUtilisation != null && cpuUtilisation > 80 ? "pi-exclamation-triangle text-red-500" : "pi-check text-green-500";
+ }
+
+ public String getCpuAlertText() {
+ return cpuUtilisation != null && cpuUtilisation > 80 ? "ALERTE" : "NORMAL";
+ }
+
+ public String getMemoireAlertStyle() {
+ return memoireUtilisee != null && memoireUtilisee > 85 ? "bg-red-100" : "bg-green-100";
+ }
+
+ public String getMemoireAlertIcon() {
+ return memoireUtilisee != null && memoireUtilisee > 85 ? "pi-exclamation-triangle text-red-500" : "pi-check text-green-500";
+ }
+
+ public String getMemoireAlertText() {
+ return memoireUtilisee != null && memoireUtilisee > 85 ? "ALERTE" : "NORMAL";
+ }
+
+ public String getDisqueAlertStyle() {
+ return disqueDisponible != null && disqueDisponible < 10 ? "bg-red-100" : "bg-green-100";
+ }
+
+ public String getDisqueAlertIcon() {
+ return disqueDisponible != null && disqueDisponible < 10 ? "pi-exclamation-triangle text-red-500" : "pi-check text-green-500";
+ }
+
+ public String getDisqueAlertText() {
+ return disqueDisponible != null && disqueDisponible < 10 ? "CRITIQUE" : "NORMAL";
+ }
+
+ // Méthodes d'actions
+ public void actualiserMonitoring() {
+ calculerMetriquesSysteme();
+ System.out.println("Monitoring actualisé");
+ }
+
+ public void nettoyerCache() {
+ System.out.println("Cache système nettoyé");
+ }
+
+ public void auditSysteme() {
+ System.out.println("Audit système lancé");
+ }
+
+ public void appliquerConfigGenerale() {
+ System.out.println("Configuration générale appliquée");
+ }
+
+ public void appliquerConfigBDD() {
+ System.out.println("Configuration BDD appliquée");
+ }
+
+ public void appliquerConfigEmail() {
+ System.out.println("Configuration email appliquée");
+ }
+
+ public void appliquerConfigSecurite() {
+ System.out.println("Configuration sécurité appliquée");
+ }
+
+ public void sauvegarderAlertes() {
+ System.out.println("Configuration des alertes sauvegardée");
+ }
+
+ public static class ConfigurationSysteme {
+ private boolean cacheActivé;
+ private int dureeCacheMinutes;
+ private int tailleLotTraitement;
+ private String niveauLog;
+ private int retentionLogJours;
+ private boolean métriquesActivées;
+ private boolean alertesSystemeActivées;
+
+ // Getters et setters
+ public boolean isCacheActivé() { return cacheActivé; }
+ public void setCacheActivé(boolean cacheActivé) { this.cacheActivé = cacheActivé; }
+
+ public int getDureeCacheMinutes() { return dureeCacheMinutes; }
+ public void setDureeCacheMinutes(int dureeCacheMinutes) { this.dureeCacheMinutes = dureeCacheMinutes; }
+
+ public int getTailleLotTraitement() { return tailleLotTraitement; }
+ public void setTailleLotTraitement(int tailleLotTraitement) { this.tailleLotTraitement = tailleLotTraitement; }
+
+ public String getNiveauLog() { return niveauLog; }
+ public void setNiveauLog(String niveauLog) { this.niveauLog = niveauLog; }
+
+ public int getRetentionLogJours() { return retentionLogJours; }
+ public void setRetentionLogJours(int retentionLogJours) { this.retentionLogJours = retentionLogJours; }
+
+ public boolean isMétriquesActivées() { return métriquesActivées; }
+ public void setMétriquesActivées(boolean métriquesActivées) { this.métriquesActivées = métriquesActivées; }
+
+ public boolean isAlertesSystemeActivées() { return alertesSystemeActivées; }
+ public void setAlertesSystemeActivées(boolean alertesSystemeActivées) { this.alertesSystemeActivées = alertesSystemeActivées; }
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/CotisationsBean.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/CotisationsBean.java
new file mode 100644
index 0000000..6200af0
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/CotisationsBean.java
@@ -0,0 +1,691 @@
+package dev.lions.unionflow.client.view;
+
+import jakarta.enterprise.context.SessionScoped;
+import jakarta.inject.Named;
+import jakarta.annotation.PostConstruct;
+import java.io.Serializable;
+import java.time.LocalDate;
+import java.time.LocalDateTime;
+import java.time.format.DateTimeFormatter;
+import java.time.temporal.ChronoUnit;
+import java.util.ArrayList;
+import java.util.List;
+import java.util.stream.Collectors;
+import java.math.BigDecimal;
+
+@Named("cotisationsBean")
+@SessionScoped
+public class CotisationsBean implements Serializable {
+
+ private static final long serialVersionUID = 1L;
+
+ private List toutesLesCotisations;
+ private List cotisationsFiltrees;
+ private List cotisationsSelectionnees;
+ private Cotisation cotisationSelectionnee;
+ private NouvelleCotisation nouvelleCotisation;
+ private Filtres filtres;
+ private StatistiquesFinancieres statistiques;
+ private List evolutionPaiements;
+ private List repartitionMethodes;
+ private List rappelsEnAttente;
+
+ @PostConstruct
+ public void init() {
+ initializeFiltres();
+ initializeStatistiques();
+ initializeCotisations();
+ initializeNouvelleCotisation();
+ initializeEvolutionPaiements();
+ initializeRepartitionMethodes();
+ initializeRappels();
+ appliquerFiltres();
+ }
+
+ private void initializeFiltres() {
+ filtres = new Filtres();
+ cotisationsSelectionnees = new ArrayList<>();
+ }
+
+ private void initializeStatistiques() {
+ statistiques = new StatistiquesFinancieres();
+ statistiques.setTotalCollecte(new BigDecimal("45750000"));
+ statistiques.setObjectifAnnuel(new BigDecimal("60000000"));
+ statistiques.setTauxRecouvrement(76.25);
+ statistiques.setCotisationsEnRetard(23);
+ statistiques.setMontantRetard(new BigDecimal("3850000"));
+ statistiques.setMoyenneMensuelle(new BigDecimal("3812500"));
+ }
+
+ private void initializeEvolutionPaiements() {
+ evolutionPaiements = new ArrayList<>();
+ String[] mois = {"Jan", "Fév", "Mar", "Avr", "Mai", "Jun", "Jul", "Aoû", "Sep", "Oct", "Nov", "Déc"};
+ BigDecimal[] montants = {
+ new BigDecimal("2850000"), new BigDecimal("3200000"), new BigDecimal("3650000"),
+ new BigDecimal("3950000"), new BigDecimal("4200000"), new BigDecimal("3800000"),
+ new BigDecimal("4100000"), new BigDecimal("3750000"), new BigDecimal("4300000"),
+ new BigDecimal("3900000"), new BigDecimal("4150000"), new BigDecimal("4000000")
+ };
+
+ for (int i = 0; i < mois.length; i++) {
+ EvolutionPaiement evolution = new EvolutionPaiement();
+ evolution.setMois(mois[i]);
+ evolution.setMontant(montants[i]);
+ evolution.setHauteur((int) (montants[i].divide(new BigDecimal("50000")).intValue()));
+ evolutionPaiements.add(evolution);
+ }
+ }
+
+ private void initializeRepartitionMethodes() {
+ repartitionMethodes = new ArrayList<>();
+
+ RepartitionMethode wave = new RepartitionMethode();
+ wave.setMethode("Wave Money");
+ wave.setPourcentage(45.2);
+ wave.setMontant(new BigDecimal("20689500"));
+ wave.setCouleur("bg-blue-500");
+ wave.setIcon("pi-mobile");
+ repartitionMethodes.add(wave);
+
+ RepartitionMethode especes = new RepartitionMethode();
+ especes.setMethode("Espèces");
+ especes.setPourcentage(32.1);
+ especes.setMontant(new BigDecimal("14690750"));
+ especes.setCouleur("bg-green-500");
+ especes.setIcon("pi-money-bill");
+ repartitionMethodes.add(especes);
+
+ RepartitionMethode cheque = new RepartitionMethode();
+ cheque.setMethode("Chèque");
+ cheque.setPourcentage(15.8);
+ cheque.setMontant(new BigDecimal("7228500"));
+ cheque.setCouleur("bg-orange-500");
+ cheque.setIcon("pi-credit-card");
+ repartitionMethodes.add(cheque);
+
+ RepartitionMethode virement = new RepartitionMethode();
+ virement.setMethode("Virement");
+ virement.setPourcentage(6.9);
+ virement.setMontant(new BigDecimal("3156750"));
+ virement.setCouleur("bg-purple-500");
+ virement.setIcon("pi-send");
+ repartitionMethodes.add(virement);
+ }
+
+ private void initializeRappels() {
+ rappelsEnAttente = new ArrayList<>();
+
+ RappelCotisation rappel1 = new RappelCotisation();
+ rappel1.setNomMembre("Jean Kouassi");
+ rappel1.setClub("Association Alpha");
+ rappel1.setMontantDu(new BigDecimal("150000"));
+ rappel1.setJoursRetard(15);
+ rappel1.setPriorite("HAUTE");
+ rappelsEnAttente.add(rappel1);
+
+ RappelCotisation rappel2 = new RappelCotisation();
+ rappel2.setNomMembre("Marie Traoré");
+ rappel2.setClub("Club Beta");
+ rappel2.setMontantDu(new BigDecimal("125000"));
+ rappel2.setJoursRetard(8);
+ rappel2.setPriorite("MOYENNE");
+ rappelsEnAttente.add(rappel2);
+
+ RappelCotisation rappel3 = new RappelCotisation();
+ rappel3.setNomMembre("Ahmed Diallo");
+ rappel3.setClub("Groupe Gamma");
+ rappel3.setMontantDu(new BigDecimal("100000"));
+ rappel3.setJoursRetard(3);
+ rappel3.setPriorite("FAIBLE");
+ rappelsEnAttente.add(rappel3);
+ }
+
+ private void initializeCotisations() {
+ toutesLesCotisations = new ArrayList<>();
+
+ String[] membres = {
+ "Jean Kouassi", "Marie Traoré", "Ahmed Diallo", "Fatou Sanogo", "Paul Ouattara",
+ "Aissata Koné", "Ibrahim Touré", "Aminata Bakayoko", "Yves Koffi", "Mariam Coulibaly",
+ "Seydou Cissé", "Adjoa Mensah", "Kwame Asante", "Ama Gyamfi", "Kofi Adjei"
+ };
+
+ String[] clubs = {
+ "Association Alpha", "Club Beta", "Groupe Gamma",
+ "Association Delta", "Club Epsilon", "Groupe Zeta",
+ "Association Eta", "Club Theta", "Groupe Iota"
+ };
+
+ String[] types = {"MENSUELLE", "TRIMESTRIELLE", "ANNUELLE", "EXCEPTIONNELLE"};
+ String[] statuts = {"PAYEE", "EN_ATTENTE", "EN_RETARD", "PARTIELLEMENT_PAYEE"};
+ String[] methodes = {"WAVE_MONEY", "ESPECES", "CHEQUE", "VIREMENT"};
+
+ BigDecimal[] montants = {
+ new BigDecimal("150000"), new BigDecimal("125000"), new BigDecimal("100000"),
+ new BigDecimal("175000"), new BigDecimal("200000"), new BigDecimal("75000"),
+ new BigDecimal("120000"), new BigDecimal("180000"), new BigDecimal("95000")
+ };
+
+ for (int i = 0; i < 50; i++) {
+ Cotisation cotisation = new Cotisation();
+ cotisation.setId((long) (i + 1));
+ cotisation.setNumeroMembre("M" + String.format("%04d", (i % membres.length) + 1));
+ cotisation.setNomMembre(membres[i % membres.length]);
+ cotisation.setClub(clubs[i % clubs.length]);
+ cotisation.setTypeCotisation(types[i % types.length]);
+ cotisation.setMontantDu(montants[i % montants.length]);
+
+ if (i % 5 == 0) {
+ cotisation.setStatut("EN_RETARD");
+ cotisation.setMontantPaye(BigDecimal.ZERO);
+ } else if (i % 8 == 0) {
+ cotisation.setStatut("PARTIELLEMENT_PAYEE");
+ cotisation.setMontantPaye(cotisation.getMontantDu().multiply(new BigDecimal("0.5")));
+ } else if (i % 12 == 0) {
+ cotisation.setStatut("EN_ATTENTE");
+ cotisation.setMontantPaye(BigDecimal.ZERO);
+ } else {
+ cotisation.setStatut("PAYEE");
+ cotisation.setMontantPaye(cotisation.getMontantDu());
+ }
+
+ cotisation.setMethodePaiement(methodes[i % methodes.length]);
+ cotisation.setDateEcheance(LocalDate.now().minusDays(i * 2).plusMonths(1));
+
+ if (!cotisation.getStatut().equals("EN_ATTENTE")) {
+ cotisation.setDatePaiement(LocalDateTime.now().minusDays(i + 1));
+ }
+
+ cotisation.setObservations(i % 7 == 0 ? "Paiement en plusieurs fois autorisé" : "");
+
+ toutesLesCotisations.add(cotisation);
+ }
+ }
+
+ private void initializeNouvelleCotisation() {
+ nouvelleCotisation = new NouvelleCotisation();
+ }
+
+ private void appliquerFiltres() {
+ cotisationsFiltrees = toutesLesCotisations.stream()
+ .filter(this::appliquerFiltre)
+ .collect(Collectors.toList());
+ }
+
+ private boolean appliquerFiltre(Cotisation cotisation) {
+ if (filtres.getNomMembre() != null && !filtres.getNomMembre().trim().isEmpty()) {
+ if (!cotisation.getNomMembre().toLowerCase().contains(filtres.getNomMembre().toLowerCase())) {
+ return false;
+ }
+ }
+
+ if (filtres.getClub() != null && !filtres.getClub().trim().isEmpty()) {
+ if (!cotisation.getClub().toLowerCase().contains(filtres.getClub().toLowerCase())) {
+ return false;
+ }
+ }
+
+ if (filtres.getStatut() != null && !filtres.getStatut().trim().isEmpty()) {
+ if (!cotisation.getStatut().equals(filtres.getStatut())) {
+ return false;
+ }
+ }
+
+ if (filtres.getTypeCotisation() != null && !filtres.getTypeCotisation().trim().isEmpty()) {
+ if (!cotisation.getTypeCotisation().equals(filtres.getTypeCotisation())) {
+ return false;
+ }
+ }
+
+ if (filtres.getMethodePaiement() != null && !filtres.getMethodePaiement().trim().isEmpty()) {
+ if (!cotisation.getMethodePaiement().equals(filtres.getMethodePaiement())) {
+ return false;
+ }
+ }
+
+ if (filtres.getDateDebut() != null) {
+ if (cotisation.getDateEcheance().isBefore(filtres.getDateDebut())) {
+ return false;
+ }
+ }
+
+ if (filtres.getDateFin() != null) {
+ if (cotisation.getDateEcheance().isAfter(filtres.getDateFin())) {
+ return false;
+ }
+ }
+
+ return true;
+ }
+
+ // Actions
+ public void rechercher() {
+ appliquerFiltres();
+ }
+
+ public void reinitialiserFiltres() {
+ filtres = new Filtres();
+ appliquerFiltres();
+ }
+
+ public void enregistrerCotisation() {
+ Cotisation nouvelleCot = new Cotisation();
+ nouvelleCot.setId((long) (toutesLesCotisations.size() + 1));
+ nouvelleCot.setNumeroMembre(nouvelleCotisation.getNumeroMembre());
+ nouvelleCot.setNomMembre(nouvelleCotisation.getNomMembre());
+ nouvelleCot.setClub(nouvelleCotisation.getClub());
+ nouvelleCot.setTypeCotisation(nouvelleCotisation.getTypeCotisation());
+ nouvelleCot.setMontantDu(nouvelleCotisation.getMontantDu());
+ nouvelleCot.setDateEcheance(nouvelleCotisation.getDateEcheance());
+ nouvelleCot.setStatut("EN_ATTENTE");
+ nouvelleCot.setMontantPaye(BigDecimal.ZERO);
+ nouvelleCot.setObservations(nouvelleCotisation.getObservations());
+
+ toutesLesCotisations.add(nouvelleCot);
+ appliquerFiltres();
+
+ System.out.println("Nouvelle cotisation enregistrée pour: " + nouvelleCot.getNomMembre());
+ initializeNouvelleCotisation();
+ }
+
+ public void marquerCommePaye() {
+ if (cotisationSelectionnee != null) {
+ cotisationSelectionnee.setStatut("PAYEE");
+ cotisationSelectionnee.setMontantPaye(cotisationSelectionnee.getMontantDu());
+ cotisationSelectionnee.setDatePaiement(LocalDateTime.now());
+ System.out.println("Cotisation marquée comme payée: " + cotisationSelectionnee.getNomMembre());
+ }
+ }
+
+ public void enregistrerPaiementPartiel() {
+ if (cotisationSelectionnee != null) {
+ cotisationSelectionnee.setStatut("PARTIELLEMENT_PAYEE");
+ cotisationSelectionnee.setDatePaiement(LocalDateTime.now());
+ System.out.println("Paiement partiel enregistré: " + cotisationSelectionnee.getNomMembre());
+ }
+ }
+
+ public void envoyerRappel() {
+ if (cotisationSelectionnee != null) {
+ System.out.println("Rappel envoyé à: " + cotisationSelectionnee.getNomMembre());
+ }
+ }
+
+ public void envoyerRappelsGroupes() {
+ System.out.println("Rappels envoyés à " + cotisationsSelectionnees.size() + " membres");
+ }
+
+ public void exporterCotisations() {
+ System.out.println("Export de " + cotisationsFiltrees.size() + " cotisations");
+ }
+
+ public void genererRapportFinancier() {
+ System.out.println("Rapport financier généré");
+ }
+
+ // Getters et Setters
+ public List getToutesLesCotisations() { return toutesLesCotisations; }
+ public void setToutesLesCotisations(List toutesLesCotisations) { this.toutesLesCotisations = toutesLesCotisations; }
+
+ public List getCotisationsFiltrees() { return cotisationsFiltrees; }
+ public void setCotisationsFiltrees(List cotisationsFiltrees) { this.cotisationsFiltrees = cotisationsFiltrees; }
+
+ public List getCotisationsSelectionnees() { return cotisationsSelectionnees; }
+ public void setCotisationsSelectionnees(List cotisationsSelectionnees) { this.cotisationsSelectionnees = cotisationsSelectionnees; }
+
+ public Cotisation getCotisationSelectionnee() { return cotisationSelectionnee; }
+ public void setCotisationSelectionnee(Cotisation cotisationSelectionnee) { this.cotisationSelectionnee = cotisationSelectionnee; }
+
+ public NouvelleCotisation getNouvelleCotisation() { return nouvelleCotisation; }
+ public void setNouvelleCotisation(NouvelleCotisation nouvelleCotisation) { this.nouvelleCotisation = nouvelleCotisation; }
+
+ public Filtres getFiltres() { return filtres; }
+ public void setFiltres(Filtres filtres) { this.filtres = filtres; }
+
+ public StatistiquesFinancieres getStatistiques() { return statistiques; }
+ public void setStatistiques(StatistiquesFinancieres statistiques) { this.statistiques = statistiques; }
+
+ public List getEvolutionPaiements() { return evolutionPaiements; }
+ public void setEvolutionPaiements(List evolutionPaiements) { this.evolutionPaiements = evolutionPaiements; }
+
+ public List getRepartitionMethodes() { return repartitionMethodes; }
+ public void setRepartitionMethodes(List repartitionMethodes) { this.repartitionMethodes = repartitionMethodes; }
+
+ public List getRappelsEnAttente() { return rappelsEnAttente; }
+ public void setRappelsEnAttente(List rappelsEnAttente) { this.rappelsEnAttente = rappelsEnAttente; }
+
+ // Classes internes
+ public static class Cotisation {
+ private Long id;
+ private String numeroMembre;
+ private String nomMembre;
+ private String club;
+ private String typeCotisation;
+ private BigDecimal montantDu;
+ private BigDecimal montantPaye;
+ private String statut;
+ private String methodePaiement;
+ private LocalDate dateEcheance;
+ private LocalDateTime datePaiement;
+ private String observations;
+
+ // Getters et setters
+ public Long getId() { return id; }
+ public void setId(Long id) { this.id = id; }
+
+ public String getNumeroMembre() { return numeroMembre; }
+ public void setNumeroMembre(String numeroMembre) { this.numeroMembre = numeroMembre; }
+
+ public String getNomMembre() { return nomMembre; }
+ public void setNomMembre(String nomMembre) { this.nomMembre = nomMembre; }
+
+ public String getClub() { return club; }
+ public void setClub(String club) { this.club = club; }
+
+ public String getTypeCotisation() { return typeCotisation; }
+ public void setTypeCotisation(String typeCotisation) { this.typeCotisation = typeCotisation; }
+
+ public BigDecimal getMontantDu() { return montantDu; }
+ public void setMontantDu(BigDecimal montantDu) { this.montantDu = montantDu; }
+
+ public BigDecimal getMontantPaye() { return montantPaye; }
+ public void setMontantPaye(BigDecimal montantPaye) { this.montantPaye = montantPaye; }
+
+ public String getStatut() { return statut; }
+ public void setStatut(String statut) { this.statut = statut; }
+
+ public String getMethodePaiement() { return methodePaiement; }
+ public void setMethodePaiement(String methodePaiement) { this.methodePaiement = methodePaiement; }
+
+ public LocalDate getDateEcheance() { return dateEcheance; }
+ public void setDateEcheance(LocalDate dateEcheance) { this.dateEcheance = dateEcheance; }
+
+ public LocalDateTime getDatePaiement() { return datePaiement; }
+ public void setDatePaiement(LocalDateTime datePaiement) { this.datePaiement = datePaiement; }
+
+ public String getObservations() { return observations; }
+ public void setObservations(String observations) { this.observations = observations; }
+
+ // Propriétés dérivées
+ public String getStatutSeverity() {
+ return switch (statut) {
+ case "PAYEE" -> "success";
+ case "EN_ATTENTE" -> "warning";
+ case "EN_RETARD" -> "danger";
+ case "PARTIELLEMENT_PAYEE" -> "info";
+ default -> "secondary";
+ };
+ }
+
+ public String getStatutIcon() {
+ return switch (statut) {
+ case "PAYEE" -> "pi-check";
+ case "EN_ATTENTE" -> "pi-clock";
+ case "EN_RETARD" -> "pi-exclamation-triangle";
+ case "PARTIELLEMENT_PAYEE" -> "pi-minus";
+ default -> "pi-circle";
+ };
+ }
+
+ public String getMethodePaiementLibelle() {
+ return switch (methodePaiement) {
+ case "WAVE_MONEY" -> "Wave Money";
+ case "ESPECES" -> "Espèces";
+ case "CHEQUE" -> "Chèque";
+ case "VIREMENT" -> "Virement";
+ default -> methodePaiement;
+ };
+ }
+
+ public String getTypeCotisationLibelle() {
+ return switch (typeCotisation) {
+ case "MENSUELLE" -> "Mensuelle";
+ case "TRIMESTRIELLE" -> "Trimestrielle";
+ case "ANNUELLE" -> "Annuelle";
+ case "EXCEPTIONNELLE" -> "Exceptionnelle";
+ default -> typeCotisation;
+ };
+ }
+
+ public String getDateEcheanceFormatee() {
+ if (dateEcheance == null) return "";
+ return dateEcheance.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 getMontantDuFormatte() {
+ return String.format("%,.0f FCFA", montantDu);
+ }
+
+ public String getMontantPayeFormatte() {
+ return String.format("%,.0f FCFA", montantPaye);
+ }
+
+ public BigDecimal getMontantRestant() {
+ return montantDu.subtract(montantPaye);
+ }
+
+ public String getMontantRestantFormatte() {
+ return String.format("%,.0f FCFA", getMontantRestant());
+ }
+
+ public int getPourcentagePaye() {
+ if (montantDu.equals(BigDecimal.ZERO)) return 0;
+ return montantPaye.multiply(new BigDecimal("100")).divide(montantDu, 0, BigDecimal.ROUND_HALF_UP).intValue();
+ }
+
+ public long getJoursRetard() {
+ if (dateEcheance == null || !statut.equals("EN_RETARD")) return 0;
+ return ChronoUnit.DAYS.between(dateEcheance, LocalDate.now());
+ }
+ }
+
+ public static class NouvelleCotisation {
+ private String numeroMembre;
+ private String nomMembre;
+ private String club;
+ private String typeCotisation;
+ private BigDecimal montantDu;
+ private LocalDate dateEcheance;
+ private String observations;
+
+ // Getters et setters
+ public String getNumeroMembre() { return numeroMembre; }
+ public void setNumeroMembre(String numeroMembre) { this.numeroMembre = numeroMembre; }
+
+ public String getNomMembre() { return nomMembre; }
+ public void setNomMembre(String nomMembre) { this.nomMembre = nomMembre; }
+
+ public String getClub() { return club; }
+ public void setClub(String club) { this.club = club; }
+
+ public String getTypeCotisation() { return typeCotisation; }
+ public void setTypeCotisation(String typeCotisation) { this.typeCotisation = typeCotisation; }
+
+ public BigDecimal getMontantDu() { return montantDu; }
+ public void setMontantDu(BigDecimal montantDu) { this.montantDu = montantDu; }
+
+ public LocalDate getDateEcheance() { return dateEcheance; }
+ public void setDateEcheance(LocalDate dateEcheance) { this.dateEcheance = dateEcheance; }
+
+ public String getObservations() { return observations; }
+ public void setObservations(String observations) { this.observations = observations; }
+ }
+
+ public static class Filtres {
+ private String nomMembre;
+ private String club;
+ private String statut;
+ private String typeCotisation;
+ private String methodePaiement;
+ private LocalDate dateDebut;
+ private LocalDate dateFin;
+
+ // Getters et setters
+ public String getNomMembre() { return nomMembre; }
+ public void setNomMembre(String nomMembre) { this.nomMembre = nomMembre; }
+
+ public String getClub() { return club; }
+ public void setClub(String club) { this.club = club; }
+
+ public String getStatut() { return statut; }
+ public void setStatut(String statut) { this.statut = statut; }
+
+ public String getTypeCotisation() { return typeCotisation; }
+ public void setTypeCotisation(String typeCotisation) { this.typeCotisation = typeCotisation; }
+
+ public String getMethodePaiement() { return methodePaiement; }
+ public void setMethodePaiement(String methodePaiement) { this.methodePaiement = methodePaiement; }
+
+ public LocalDate getDateDebut() { return dateDebut; }
+ public void setDateDebut(LocalDate dateDebut) { this.dateDebut = dateDebut; }
+
+ public LocalDate getDateFin() { return dateFin; }
+ public void setDateFin(LocalDate dateFin) { this.dateFin = dateFin; }
+ }
+
+ public static class StatistiquesFinancieres {
+ private BigDecimal totalCollecte;
+ private BigDecimal objectifAnnuel;
+ private double tauxRecouvrement;
+ private int cotisationsEnRetard;
+ private BigDecimal montantRetard;
+ private BigDecimal moyenneMensuelle;
+
+ // Getters et setters
+ public BigDecimal getTotalCollecte() { return totalCollecte; }
+ public void setTotalCollecte(BigDecimal totalCollecte) { this.totalCollecte = totalCollecte; }
+
+ public BigDecimal getObjectifAnnuel() { return objectifAnnuel; }
+ public void setObjectifAnnuel(BigDecimal objectifAnnuel) { this.objectifAnnuel = objectifAnnuel; }
+
+ public double getTauxRecouvrement() { return tauxRecouvrement; }
+ public void setTauxRecouvrement(double tauxRecouvrement) { this.tauxRecouvrement = tauxRecouvrement; }
+
+ public int getCotisationsEnRetard() { return cotisationsEnRetard; }
+ public void setCotisationsEnRetard(int cotisationsEnRetard) { this.cotisationsEnRetard = cotisationsEnRetard; }
+
+ public BigDecimal getMontantRetard() { return montantRetard; }
+ public void setMontantRetard(BigDecimal montantRetard) { this.montantRetard = montantRetard; }
+
+ public BigDecimal getMoyenneMensuelle() { return moyenneMensuelle; }
+ public void setMoyenneMensuelle(BigDecimal moyenneMensuelle) { this.moyenneMensuelle = moyenneMensuelle; }
+
+ // Méthodes de formatage
+ public String getTotalCollecteFormatte() {
+ return String.format("%,.0f FCFA", totalCollecte);
+ }
+
+ public String getObjectifAnnuelFormatte() {
+ return String.format("%,.0f FCFA", objectifAnnuel);
+ }
+
+ public String getMontantRetardFormatte() {
+ return String.format("%,.0f FCFA", montantRetard);
+ }
+
+ public String getMoyenneMensuelleFormattee() {
+ return String.format("%,.0f FCFA", moyenneMensuelle);
+ }
+
+ public int getTauxRecouvrementInt() {
+ return (int) tauxRecouvrement;
+ }
+ }
+
+ public static class EvolutionPaiement {
+ private String mois;
+ private BigDecimal montant;
+ private int hauteur;
+
+ // Getters et setters
+ public String getMois() { return mois; }
+ public void setMois(String mois) { this.mois = mois; }
+
+ public BigDecimal getMontant() { return montant; }
+ public void setMontant(BigDecimal montant) { this.montant = montant; }
+
+ public int getHauteur() { return hauteur; }
+ public void setHauteur(int hauteur) { this.hauteur = hauteur; }
+
+ public String getMontantFormatte() {
+ return String.format("%.1fM", montant.divide(new BigDecimal("1000000")).doubleValue());
+ }
+ }
+
+ public static class RepartitionMethode {
+ private String methode;
+ private double pourcentage;
+ private BigDecimal montant;
+ private String couleur;
+ private String icon;
+
+ // Getters et setters
+ public String getMethode() { return methode; }
+ public void setMethode(String methode) { this.methode = methode; }
+
+ public double getPourcentage() { return pourcentage; }
+ public void setPourcentage(double pourcentage) { this.pourcentage = pourcentage; }
+
+ public BigDecimal getMontant() { return montant; }
+ public void setMontant(BigDecimal montant) { this.montant = montant; }
+
+ public String getCouleur() { return couleur; }
+ public void setCouleur(String couleur) { this.couleur = couleur; }
+
+ public String getIcon() { return icon; }
+ public void setIcon(String icon) { this.icon = icon; }
+
+ public String getMontantFormatte() {
+ return String.format("%,.0f FCFA", montant);
+ }
+
+ public int getPourcentageInt() {
+ return (int) pourcentage;
+ }
+
+ public int getLargeur() {
+ return (int) (pourcentage * 2);
+ }
+ }
+
+ public static class RappelCotisation {
+ private String nomMembre;
+ private String club;
+ private BigDecimal montantDu;
+ private int joursRetard;
+ private String priorite;
+
+ // Getters et setters
+ public String getNomMembre() { return nomMembre; }
+ public void setNomMembre(String nomMembre) { this.nomMembre = nomMembre; }
+
+ public String getClub() { return club; }
+ public void setClub(String club) { this.club = club; }
+
+ public BigDecimal getMontantDu() { return montantDu; }
+ public void setMontantDu(BigDecimal montantDu) { this.montantDu = montantDu; }
+
+ public int getJoursRetard() { return joursRetard; }
+ public void setJoursRetard(int joursRetard) { this.joursRetard = joursRetard; }
+
+ public String getPriorite() { return priorite; }
+ public void setPriorite(String priorite) { this.priorite = priorite; }
+
+ public String getMontantDuFormatte() {
+ return String.format("%,.0f FCFA", montantDu);
+ }
+
+ public String getPrioriteSeverity() {
+ return switch (priorite) {
+ case "HAUTE" -> "danger";
+ case "MOYENNE" -> "warning";
+ case "FAIBLE" -> "info";
+ default -> "secondary";
+ };
+ }
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/CotisationsGestionBean.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/CotisationsGestionBean.java
new file mode 100644
index 0000000..6cf6dc9
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/CotisationsGestionBean.java
@@ -0,0 +1,699 @@
+package dev.lions.unionflow.client.view;
+
+import jakarta.enterprise.context.SessionScoped;
+import jakarta.inject.Named;
+import jakarta.annotation.PostConstruct;
+import java.io.Serializable;
+import java.math.BigDecimal;
+import java.time.LocalDate;
+import java.time.format.DateTimeFormatter;
+import java.util.ArrayList;
+import java.util.List;
+import java.util.stream.Collectors;
+
+@Named("cotisationsGestionBean")
+@SessionScoped
+public class CotisationsGestionBean implements Serializable {
+
+ private static final long serialVersionUID = 1L;
+
+ // Propriétés principales
+ private String periodeActuelle;
+ private BigDecimal tauxRecouvrement;
+ private int totalMembresActifs;
+
+ // KPIs financiers
+ private String montantCollecte;
+ private String objectifMensuel;
+ private int progressionMensuelle;
+ private String membresAJour;
+ private int pourcentageMembresAJour;
+ private String montantEnAttente;
+ private int nombreCotisationsEnAttente;
+ private String montantImpayes;
+ private int joursRetardMoyen;
+ private String revenus2024;
+ private String croissanceAnnuelle;
+ private String prelevementsActifs;
+ private String montantPrelevementsPrevu;
+
+ // Analytics
+ private String periodeGraphique = "12M";
+ private List topOrganisations;
+ private int paiementsWave = 65;
+ private int paiementsVirement = 25;
+ private int paiementsEspeces = 10;
+
+ // Filtres
+ private FiltresCotisations filtres;
+ private List listeOrganisations;
+
+ // Données et sélections
+ private List cotisationsFiltrees;
+ private List cotisationsSelectionnees;
+ private String montantTotalSelectionne;
+
+ // Wave Money
+ private int membresPrelevementActif;
+ private String montantPrelevementMensuel;
+ private String prochainPrelevement;
+
+ // Nouvelle campagne
+ private NouvelleCampagne nouvelleCampagne;
+
+ @PostConstruct
+ public void init() {
+ initializeKPIs();
+ initializeFiltres();
+ initializeData();
+ initializeTopOrganisations();
+ initializeNouvelleCampagne();
+ }
+
+ private void initializeKPIs() {
+ this.periodeActuelle = "Décembre 2024";
+ this.tauxRecouvrement = new BigDecimal("87.3");
+ this.totalMembresActifs = 18547;
+
+ this.montantCollecte = "2,845,000 FCFA";
+ this.objectifMensuel = "3,200,000 FCFA";
+ this.progressionMensuelle = 89;
+ this.membresAJour = "16,205";
+ this.pourcentageMembresAJour = 87;
+ this.montantEnAttente = "785,000 FCFA";
+ this.nombreCotisationsEnAttente = 1247;
+ this.montantImpayes = "425,000 FCFA";
+ this.joursRetardMoyen = 12;
+ this.revenus2024 = "34,200,000 FCFA";
+ this.croissanceAnnuelle = "+15.3%";
+ this.prelevementsActifs = "8,450";
+ this.montantPrelevementsPrevu = "42,250,000";
+
+ this.membresPrelevementActif = 8450;
+ this.montantPrelevementMensuel = "42,250,000 FCFA";
+ this.prochainPrelevement = "01/01/2025";
+
+ this.cotisationsSelectionnees = new ArrayList<>();
+ this.montantTotalSelectionne = "0 FCFA";
+ }
+
+ private void initializeFiltres() {
+ this.filtres = new FiltresCotisations();
+ this.listeOrganisations = new ArrayList<>();
+
+ // Simulation d'organisations
+ for (int i = 1; i <= 127; i++) {
+ Organisation org = new Organisation();
+ org.setId((long) i);
+ org.setNom("Organisation " + i);
+ listeOrganisations.add(org);
+ }
+ }
+
+ private void initializeData() {
+ this.cotisationsFiltrees = new ArrayList<>();
+
+ // Simulation de données de cotisations pour les 127 organisations
+ for (int i = 1; i <= 500; i++) {
+ CotisationAdmin cotisation = new CotisationAdmin();
+ cotisation.setId((long) i);
+ cotisation.setNomOrganisation("Organisation " + ((i % 127) + 1));
+ cotisation.setRegionOrganisation("Région " + ((i % 12) + 1));
+ cotisation.setIconeOrganisation("pi-building");
+
+ cotisation.setNomCompletMembre("Membre " + i);
+ cotisation.setNumeroMembre("M" + String.format("%06d", i));
+ cotisation.setInitialesMembre(getInitiales("Membre " + i));
+ cotisation.setTypeMembre(i % 3 == 0 ? "Membre Actif" : "Membre Associé");
+
+ cotisation.setType(getTypeCotisation(i));
+ cotisation.setPeriode(getperiode(i));
+ cotisation.setAnnee("2024");
+ cotisation.setMontant(new BigDecimal(getMontantCotisation(i)));
+ cotisation.setStatut(getStatutCotisation(i));
+ cotisation.setDateEcheance(LocalDate.now().minusDays(i % 60));
+
+ if (cotisation.getStatut().equals("PAYE")) {
+ cotisation.setDatePaiement(cotisation.getDateEcheance().plusDays(i % 10));
+ cotisation.setModePaiement(getModePaiement(i));
+ }
+
+ cotisationsFiltrees.add(cotisation);
+ }
+ }
+
+ private void initializeTopOrganisations() {
+ this.topOrganisations = new ArrayList<>();
+
+ String[] noms = {"Lions Club Dakar Centre", "Association Thiès Nord", "Groupe Kaolack Est",
+ "Lions Club Saint-Louis", "Association Louga Centre"};
+ int[] taux = {98, 95, 92, 89, 87};
+ String[] montants = {"485K", "420K", "380K", "365K", "340K"};
+ int[] membres = {156, 134, 128, 145, 120};
+ int[] totaux = {160, 145, 140, 165, 135};
+
+ for (int i = 0; i < noms.length; i++) {
+ OrganisationPerformante org = new OrganisationPerformante();
+ org.setNom(noms[i]);
+ org.setTauxRecouvrement(taux[i]);
+ org.setMontantCollecte(montants[i]);
+ org.setNombreMembresAJour(membres[i]);
+ org.setTotalMembres(totaux[i]);
+ topOrganisations.add(org);
+ }
+ }
+
+ private void initializeNouvelleCampagne() {
+ this.nouvelleCampagne = new NouvelleCampagne();
+ }
+
+ private String getTypeCotisation(int i) {
+ return switch (i % 4) {
+ case 0 -> "MENSUELLE";
+ case 1 -> "SPECIALE";
+ case 2 -> "ADHESION";
+ default -> "EVENEMENT";
+ };
+ }
+
+ private String getperiode(int i) {
+ String[] mois = {"Janvier", "Février", "Mars", "Avril", "Mai", "Juin",
+ "Juillet", "Août", "Septembre", "Octobre", "Novembre", "Décembre"};
+ return mois[i % 12] + " 2024";
+ }
+
+ private int getMontantCotisation(int i) {
+ return switch (i % 4) {
+ case 0 -> 5000; // Mensuelle
+ case 1 -> 15000; // Spéciale
+ case 2 -> 25000; // Adhésion
+ default -> 10000; // Événement
+ };
+ }
+
+ private String getStatutCotisation(int i) {
+ return switch (i % 4) {
+ case 0 -> "PAYE";
+ case 1 -> "EN_ATTENTE";
+ case 2 -> "EN_RETARD";
+ default -> "PAYE";
+ };
+ }
+
+ private String getModePaiement(int i) {
+ return switch (i % 3) {
+ case 0 -> "WAVE";
+ case 1 -> "VIREMENT";
+ default -> "ESPECES";
+ };
+ }
+
+ private String getInitiales(String nom) {
+ String[] parts = nom.split(" ");
+ return parts.length >= 2 ?
+ String.valueOf(parts[0].charAt(0)) + String.valueOf(parts[1].charAt(0)) :
+ String.valueOf(nom.charAt(0)) + "M";
+ }
+
+ // Actions principales
+ public void creerCampagne() {
+ System.out.println("Création de la campagne: " + nouvelleCampagne.getNom());
+ // Logique de création de campagne
+ initializeNouvelleCampagne(); // Reset pour nouvelle campagne
+ }
+
+ public void relancesGroupees() {
+ System.out.println("Envoi de relances groupées");
+ }
+
+ public void exporterTout() {
+ System.out.println("Export global des cotisations");
+ }
+
+ public void appliquerFiltres() {
+ // Logique de filtrage
+ System.out.println("Application des filtres");
+ }
+
+ public void reinitialiserFiltres() {
+ this.filtres = new FiltresCotisations();
+ System.out.println("Réinitialisation des filtres");
+ }
+
+ public void exporterExcel() {
+ System.out.println("Export Excel des cotisations filtrées");
+ }
+
+ // Actions sur cotisations individuelles
+ public void enregistrerPaiement(CotisationAdmin cotisation) {
+ System.out.println("Enregistrement paiement pour: " + cotisation.getNumeroMembre());
+ }
+
+ public void genererRecu(CotisationAdmin cotisation) {
+ System.out.println("Génération reçu pour: " + cotisation.getNumeroMembre());
+ }
+
+ public void envoyerRappel(CotisationAdmin cotisation) {
+ System.out.println("Envoi rappel pour: " + cotisation.getNumeroMembre());
+ }
+
+ public void voirDetails(CotisationAdmin cotisation) {
+ System.out.println("Affichage détails pour: " + cotisation.getNumeroMembre());
+ }
+
+ // Actions groupées
+ public void marquerPayeesGroupees() {
+ System.out.println("Marquage " + cotisationsSelectionnees.size() + " cotisations comme payées");
+ }
+
+ public void envoyerRelancesGroupees() {
+ System.out.println("Envoi relances pour " + cotisationsSelectionnees.size() + " cotisations");
+ }
+
+ public void genererRecusGroupes() {
+ System.out.println("Génération reçus pour " + cotisationsSelectionnees.size() + " cotisations");
+ }
+
+ public void annulerCotisationsGroupees() {
+ System.out.println("Annulation " + cotisationsSelectionnees.size() + " cotisations");
+ }
+
+ // Wave Money
+ public void lancerPrelevements() {
+ System.out.println("Lancement des prélèvements Wave Money");
+ }
+
+ public void testerAPIWave() {
+ System.out.println("Test de l'API Wave Money");
+ }
+
+ public void voirHistoriquePrelevements() {
+ System.out.println("Affichage historique des prélèvements");
+ }
+
+ // Actions rapides
+ public void genererRapportMensuel() {
+ System.out.println("Génération rapport mensuel");
+ }
+
+ public void configurerRelancesAuto() {
+ System.out.println("Configuration relances automatiques");
+ }
+
+ public void gererTypesCotisations() {
+ System.out.println("Gestion des types de cotisations");
+ }
+
+ public void tableauDeBord() {
+ System.out.println("Affichage tableau de bord");
+ }
+
+ // Getters et Setters
+ public String getPeriodeActuelle() { return periodeActuelle; }
+ public void setPeriodeActuelle(String periodeActuelle) { this.periodeActuelle = periodeActuelle; }
+
+ public BigDecimal getTauxRecouvrement() { return tauxRecouvrement; }
+ public void setTauxRecouvrement(BigDecimal tauxRecouvrement) { this.tauxRecouvrement = tauxRecouvrement; }
+
+ public int getTotalMembresActifs() { return totalMembresActifs; }
+ public void setTotalMembresActifs(int totalMembresActifs) { this.totalMembresActifs = totalMembresActifs; }
+
+ public String getMontantCollecte() { return montantCollecte; }
+ public void setMontantCollecte(String montantCollecte) { this.montantCollecte = montantCollecte; }
+
+ public String getObjectifMensuel() { return objectifMensuel; }
+ public void setObjectifMensuel(String objectifMensuel) { this.objectifMensuel = objectifMensuel; }
+
+ public int getProgressionMensuelle() { return progressionMensuelle; }
+ public void setProgressionMensuelle(int progressionMensuelle) { this.progressionMensuelle = progressionMensuelle; }
+
+ public String getMembresAJour() { return membresAJour; }
+ public void setMembresAJour(String membresAJour) { this.membresAJour = membresAJour; }
+
+ public int getPourcentageMembresAJour() { return pourcentageMembresAJour; }
+ public void setPourcentageMembresAJour(int pourcentageMembresAJour) { this.pourcentageMembresAJour = pourcentageMembresAJour; }
+
+ public String getMontantEnAttente() { return montantEnAttente; }
+ public void setMontantEnAttente(String montantEnAttente) { this.montantEnAttente = montantEnAttente; }
+
+ public int getNombreCotisationsEnAttente() { return nombreCotisationsEnAttente; }
+ public void setNombreCotisationsEnAttente(int nombreCotisationsEnAttente) { this.nombreCotisationsEnAttente = nombreCotisationsEnAttente; }
+
+ public String getMontantImpayes() { return montantImpayes; }
+ public void setMontantImpayes(String montantImpayes) { this.montantImpayes = montantImpayes; }
+
+ public int getJoursRetardMoyen() { return joursRetardMoyen; }
+ public void setJoursRetardMoyen(int joursRetardMoyen) { this.joursRetardMoyen = joursRetardMoyen; }
+
+ public String getRevenus2024() { return revenus2024; }
+ public void setRevenus2024(String revenus2024) { this.revenus2024 = revenus2024; }
+
+ public String getCroissanceAnnuelle() { return croissanceAnnuelle; }
+ public void setCroissanceAnnuelle(String croissanceAnnuelle) { this.croissanceAnnuelle = croissanceAnnuelle; }
+
+ public String getPrelevementsActifs() { return prelevementsActifs; }
+ public void setPrelevementsActifs(String prelevementsActifs) { this.prelevementsActifs = prelevementsActifs; }
+
+ public String getMontantPrelevementsPrevu() { return montantPrelevementsPrevu; }
+ public void setMontantPrelevementsPrevu(String montantPrelevementsPrevu) { this.montantPrelevementsPrevu = montantPrelevementsPrevu; }
+
+ public String getPeriodeGraphique() { return periodeGraphique; }
+ public void setPeriodeGraphique(String periodeGraphique) { this.periodeGraphique = periodeGraphique; }
+
+ public List getTopOrganisations() { return topOrganisations; }
+ public void setTopOrganisations(List topOrganisations) { this.topOrganisations = topOrganisations; }
+
+ public int getPaiementsWave() { return paiementsWave; }
+ public void setPaiementsWave(int paiementsWave) { this.paiementsWave = paiementsWave; }
+
+ public int getPaiementsVirement() { return paiementsVirement; }
+ public void setPaiementsVirement(int paiementsVirement) { this.paiementsVirement = paiementsVirement; }
+
+ public int getPaiementsEspeces() { return paiementsEspeces; }
+ public void setPaiementsEspeces(int paiementsEspeces) { this.paiementsEspeces = paiementsEspeces; }
+
+ public FiltresCotisations getFiltres() { return filtres; }
+ public void setFiltres(FiltresCotisations filtres) { this.filtres = filtres; }
+
+ public List getListeOrganisations() { return listeOrganisations; }
+ public void setListeOrganisations(List listeOrganisations) { this.listeOrganisations = listeOrganisations; }
+
+ public List getCotisationsFiltrees() { return cotisationsFiltrees; }
+ public void setCotisationsFiltrees(List cotisationsFiltrees) { this.cotisationsFiltrees = cotisationsFiltrees; }
+
+ public List getCotisationsSelectionnees() { return cotisationsSelectionnees; }
+ public void setCotisationsSelectionnees(List cotisationsSelectionnees) {
+ this.cotisationsSelectionnees = cotisationsSelectionnees;
+ calculerMontantTotalSelectionne();
+ }
+
+ public String getMontantTotalSelectionne() { return montantTotalSelectionne; }
+ public void setMontantTotalSelectionne(String montantTotalSelectionne) { this.montantTotalSelectionne = montantTotalSelectionne; }
+
+ public int getMembresPrelevementActif() { return membresPrelevementActif; }
+ public void setMembresPrelevementActif(int membresPrelevementActif) { this.membresPrelevementActif = membresPrelevementActif; }
+
+ public String getMontantPrelevementMensuel() { return montantPrelevementMensuel; }
+ public void setMontantPrelevementMensuel(String montantPrelevementMensuel) { this.montantPrelevementMensuel = montantPrelevementMensuel; }
+
+ public String getProchainPrelevement() { return prochainPrelevement; }
+ public void setProchainPrelevement(String prochainPrelevement) { this.prochainPrelevement = prochainPrelevement; }
+
+ public NouvelleCampagne getNouvelleCampagne() { return nouvelleCampagne; }
+ public void setNouvelleCampagne(NouvelleCampagne nouvelleCampagne) { this.nouvelleCampagne = nouvelleCampagne; }
+
+ private void calculerMontantTotalSelectionne() {
+ if (cotisationsSelectionnees != null && !cotisationsSelectionnees.isEmpty()) {
+ BigDecimal total = cotisationsSelectionnees.stream()
+ .map(CotisationAdmin::getMontant)
+ .reduce(BigDecimal.ZERO, BigDecimal::add);
+ this.montantTotalSelectionne = String.format("%,.0f FCFA", total);
+ } else {
+ this.montantTotalSelectionne = "0 FCFA";
+ }
+ }
+
+ // Classes internes pour les données
+ public static class CotisationAdmin {
+ private Long id;
+ private String nomOrganisation;
+ private String regionOrganisation;
+ private String iconeOrganisation;
+ private String nomCompletMembre;
+ private String numeroMembre;
+ private String initialesMembre;
+ private String typeMembre;
+ private String type;
+ private String periode;
+ private String annee;
+ private BigDecimal montant;
+ private String statut;
+ private LocalDate dateEcheance;
+ private LocalDate datePaiement;
+ private String modePaiement;
+
+ // Getters et setters
+ public Long getId() { return id; }
+ public void setId(Long id) { this.id = id; }
+
+ public String getNomOrganisation() { return nomOrganisation; }
+ public void setNomOrganisation(String nomOrganisation) { this.nomOrganisation = nomOrganisation; }
+
+ public String getRegionOrganisation() { return regionOrganisation; }
+ public void setRegionOrganisation(String regionOrganisation) { this.regionOrganisation = regionOrganisation; }
+
+ public String getIconeOrganisation() { return iconeOrganisation; }
+ public void setIconeOrganisation(String iconeOrganisation) { this.iconeOrganisation = iconeOrganisation; }
+
+ public String getNomCompletMembre() { return nomCompletMembre; }
+ public void setNomCompletMembre(String nomCompletMembre) { this.nomCompletMembre = nomCompletMembre; }
+
+ public String getNumeroMembre() { return numeroMembre; }
+ public void setNumeroMembre(String numeroMembre) { this.numeroMembre = numeroMembre; }
+
+ public String getInitialesMembre() { return initialesMembre; }
+ public void setInitialesMembre(String initialesMembre) { this.initialesMembre = initialesMembre; }
+
+ public String getTypeMembre() { return typeMembre; }
+ public void setTypeMembre(String typeMembre) { this.typeMembre = typeMembre; }
+
+ public String getType() { return type; }
+ public void setType(String type) { this.type = type; }
+
+ public String getPeriode() { return periode; }
+ public void setPeriode(String periode) { this.periode = periode; }
+
+ public String getAnnee() { return annee; }
+ public void setAnnee(String annee) { this.annee = annee; }
+
+ public BigDecimal getMontant() { return montant; }
+ public void setMontant(BigDecimal montant) { this.montant = montant; }
+
+ public String getStatut() { return statut; }
+ public void setStatut(String statut) { this.statut = statut; }
+
+ public LocalDate getDateEcheance() { return dateEcheance; }
+ public void setDateEcheance(LocalDate dateEcheance) { this.dateEcheance = dateEcheance; }
+
+ public LocalDate getDatePaiement() { return datePaiement; }
+ public void setDatePaiement(LocalDate datePaiement) { this.datePaiement = datePaiement; }
+
+ public String getModePaiement() { return modePaiement; }
+ public void setModePaiement(String modePaiement) { this.modePaiement = modePaiement; }
+
+ // Propriétés dérivées pour l'affichage
+ public String getTypeLibelle() {
+ return switch (type) {
+ case "MENSUELLE" -> "Mensuelle";
+ case "SPECIALE" -> "Spéciale";
+ case "ADHESION" -> "Adhésion";
+ case "EVENEMENT" -> "Événement";
+ default -> type;
+ };
+ }
+
+ public String getTypeSeverity() {
+ return switch (type) {
+ case "MENSUELLE" -> "info";
+ case "SPECIALE" -> "warning";
+ case "ADHESION" -> "success";
+ case "EVENEMENT" -> "primary";
+ default -> "secondary";
+ };
+ }
+
+ public String getTypeIcon() {
+ return switch (type) {
+ case "MENSUELLE" -> "pi-calendar";
+ case "SPECIALE" -> "pi-star";
+ case "ADHESION" -> "pi-user-plus";
+ case "EVENEMENT" -> "pi-calendar-plus";
+ default -> "pi-circle";
+ };
+ }
+
+ public String getMontantFormatte() {
+ return String.format("%,.0f", montant);
+ }
+
+ public String getStatutLibelle() {
+ return switch (statut) {
+ case "PAYE" -> "Payée";
+ case "EN_ATTENTE" -> "En attente";
+ case "EN_RETARD" -> "En retard";
+ case "ANNULE" -> "Annulée";
+ default -> statut;
+ };
+ }
+
+ public String getStatutSeverity() {
+ return switch (statut) {
+ case "PAYE" -> "success";
+ case "EN_ATTENTE" -> "warning";
+ case "EN_RETARD" -> "danger";
+ case "ANNULE" -> "secondary";
+ default -> "secondary";
+ };
+ }
+
+ public String getStatutIcon() {
+ return switch (statut) {
+ case "PAYE" -> "pi-check";
+ case "EN_ATTENTE" -> "pi-clock";
+ case "EN_RETARD" -> "pi-exclamation-triangle";
+ case "ANNULE" -> "pi-times";
+ default -> "pi-circle";
+ };
+ }
+
+ public String getDateEcheanceFormattee() {
+ return dateEcheance != null ? dateEcheance.format(DateTimeFormatter.ofPattern("dd/MM/yyyy")) : "";
+ }
+
+ public String getDatePaiementFormattee() {
+ return datePaiement != null ? datePaiement.format(DateTimeFormatter.ofPattern("dd/MM/yyyy")) : "";
+ }
+
+ public String getRetardTexte() {
+ if (dateEcheance == null) return "";
+ long jours = java.time.temporal.ChronoUnit.DAYS.between(dateEcheance, LocalDate.now());
+ if (jours <= 0) return "À temps";
+ if (jours <= 7) return jours + "j retard";
+ if (jours <= 30) return jours + "j retard";
+ return "+30j retard";
+ }
+
+ public String getRetardCouleur() {
+ if (dateEcheance == null) return "text-600";
+ long jours = java.time.temporal.ChronoUnit.DAYS.between(dateEcheance, LocalDate.now());
+ if (jours <= 0) return "text-green-500";
+ if (jours <= 7) return "text-orange-500";
+ return "text-red-500";
+ }
+
+ public String getModePaiementLibelle() {
+ return switch (modePaiement != null ? modePaiement : "") {
+ case "WAVE" -> "Wave Money";
+ case "VIREMENT" -> "Virement";
+ case "ESPECES" -> "Espèces";
+ case "ORANGE" -> "Orange Money";
+ default -> modePaiement;
+ };
+ }
+
+ public String getModePaiementIcon() {
+ return switch (modePaiement != null ? modePaiement : "") {
+ case "WAVE" -> "pi-mobile";
+ case "VIREMENT" -> "pi-building";
+ case "ESPECES" -> "pi-money-bill";
+ case "ORANGE" -> "pi-mobile";
+ default -> "pi-circle";
+ };
+ }
+ }
+
+ public static class FiltresCotisations {
+ private String organisation = "";
+ private String periode = "MOIS";
+ private String statut = "";
+ private String type = "";
+ private String recherche = "";
+ private BigDecimal montantMin;
+ private BigDecimal montantMax;
+ private String retardJours = "";
+ private String modePaiement = "";
+
+ // Getters et setters
+ public String getOrganisation() { return organisation; }
+ public void setOrganisation(String organisation) { this.organisation = organisation; }
+
+ public String getPeriode() { return periode; }
+ public void setPeriode(String periode) { this.periode = periode; }
+
+ public String getStatut() { return statut; }
+ public void setStatut(String statut) { this.statut = statut; }
+
+ public String getType() { return type; }
+ public void setType(String type) { this.type = type; }
+
+ public String getRecherche() { return recherche; }
+ public void setRecherche(String recherche) { this.recherche = recherche; }
+
+ public BigDecimal getMontantMin() { return montantMin; }
+ public void setMontantMin(BigDecimal montantMin) { this.montantMin = montantMin; }
+
+ public BigDecimal getMontantMax() { return montantMax; }
+ public void setMontantMax(BigDecimal montantMax) { this.montantMax = montantMax; }
+
+ public String getRetardJours() { return retardJours; }
+ public void setRetardJours(String retardJours) { this.retardJours = retardJours; }
+
+ public String getModePaiement() { return modePaiement; }
+ public void setModePaiement(String modePaiement) { this.modePaiement = modePaiement; }
+ }
+
+ public static class Organisation {
+ private Long id;
+ private String nom;
+
+ public Long getId() { return id; }
+ public void setId(Long id) { this.id = id; }
+
+ public String getNom() { return nom; }
+ public void setNom(String nom) { this.nom = nom; }
+ }
+
+ public static class OrganisationPerformante {
+ private String nom;
+ private int tauxRecouvrement;
+ private String montantCollecte;
+ private int nombreMembresAJour;
+ private int totalMembres;
+
+ public String getNom() { return nom; }
+ public void setNom(String nom) { this.nom = nom; }
+
+ public int getTauxRecouvrement() { return tauxRecouvrement; }
+ public void setTauxRecouvrement(int tauxRecouvrement) { this.tauxRecouvrement = tauxRecouvrement; }
+
+ public String getMontantCollecte() { return montantCollecte; }
+ public void setMontantCollecte(String montantCollecte) { this.montantCollecte = montantCollecte; }
+
+ public int getNombreMembresAJour() { return nombreMembresAJour; }
+ public void setNombreMembresAJour(int nombreMembresAJour) { this.nombreMembresAJour = nombreMembresAJour; }
+
+ public int getTotalMembres() { return totalMembres; }
+ public void setTotalMembres(int totalMembres) { this.totalMembres = totalMembres; }
+ }
+
+ public static class NouvelleCampagne {
+ private String nom;
+ private String type;
+ private BigDecimal montant;
+ private LocalDate dateEcheance;
+ private String scope = "TOUTES";
+ private String description;
+ private boolean relanceAutomatique = true;
+
+ public String getNom() { return nom; }
+ public void setNom(String nom) { this.nom = nom; }
+
+ public String getType() { return type; }
+ public void setType(String type) { this.type = type; }
+
+ public BigDecimal getMontant() { return montant; }
+ public void setMontant(BigDecimal montant) { this.montant = montant; }
+
+ public LocalDate getDateEcheance() { return dateEcheance; }
+ public void setDateEcheance(LocalDate dateEcheance) { this.dateEcheance = dateEcheance; }
+
+ public String getScope() { return scope; }
+ public void setScope(String scope) { this.scope = scope; }
+
+ public String getDescription() { return description; }
+ public void setDescription(String description) { this.description = description; }
+
+ public boolean isRelanceAutomatique() { return relanceAutomatique; }
+ public void setRelanceAutomatique(boolean relanceAutomatique) { this.relanceAutomatique = relanceAutomatique; }
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/DashboardBean.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/DashboardBean.java
new file mode 100644
index 0000000..0a44ce3
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/DashboardBean.java
@@ -0,0 +1,349 @@
+package dev.lions.unionflow.client.view;
+
+import jakarta.enterprise.context.RequestScoped;
+import jakarta.inject.Named;
+import java.io.Serializable;
+import java.time.LocalDate;
+import java.time.LocalDateTime;
+import java.time.format.DateTimeFormatter;
+import java.util.ArrayList;
+import java.util.Date;
+import java.util.List;
+
+@Named("dashboardBean")
+@RequestScoped
+public class DashboardBean implements Serializable {
+
+ private static final long serialVersionUID = 1L;
+
+ // Propriétés existantes
+ private int activeMembers = 245;
+ private String totalCotisations = "12,450,000";
+ private int pendingAides = 7;
+ private int upcomingEvents = 3;
+
+ // Nouvelles propriétés pour le dashboard enrichi
+ private int totalMembers = 268;
+ private String aidesDistribuees = "3,200,000";
+ private int tauxParticipation = 78;
+
+ // Propriétés pour les alertes
+ private int cotisationsRetard = 12;
+ private int adhesionsExpiration = 8;
+ private int demandesToTraiter = 15;
+ private int tachesFinaliser = 4;
+
+ // Propriétés pour les évolutions
+ private int membresEvolutionPourcent = 8;
+ private int cotisationsEvolutionPourcent = 15;
+ private String objectifCotisations = "15,000,000";
+ private int aidesApprouvees = 12;
+ private int membresParticipants = 189;
+
+ // Propriétés pour le graphique
+ private String periodeGraph = "3M";
+ private String filtreActivite = "ALL";
+
+ // Propriétés pour les cotisations
+ private int cotisationsAJour = 60;
+ private int cotisationsRetardPourcent = 20;
+ private int cotisationsImpayees = 20;
+
+ // Propriétés pour les tâches prioritaires
+ private int adhesionsPendantes = 5;
+ private int aidesEnAttente = 7;
+ private int evenementsAPlanifier = 2;
+
+ // Propriétés financières
+ private Date moisSelectionne = new Date();
+ private String recettesMois = "4,250,000";
+ private String depensesMois = "1,800,000";
+ private String soldeMois = "2,450,000";
+ private String tresorerie = "18,750,000";
+
+ // Date actuelle
+ private String currentDate;
+
+ // Propriétés manquantes pour les barres de progression
+ private int tauxActivite = 75;
+ private int tauxObjectifCotisations = 82;
+ private int tauxAidesTraitees = 68;
+ private int tauxEngagement = 89;
+ private int tachesCompletees = 23;
+ private boolean hasAlerts = true;
+
+ public DashboardBean() {
+ this.currentDate = LocalDate.now().format(DateTimeFormatter.ofPattern("dd MMMM yyyy"));
+ }
+
+ // Getters et Setters complets
+ public int getActiveMembers() { return activeMembers; }
+ public void setActiveMembers(int activeMembers) { this.activeMembers = activeMembers; }
+
+ public String getTotalCotisations() { return totalCotisations; }
+ public void setTotalCotisations(String totalCotisations) { this.totalCotisations = totalCotisations; }
+
+ public int getPendingAides() { return pendingAides; }
+ public void setPendingAides(int pendingAides) { this.pendingAides = pendingAides; }
+
+ public int getUpcomingEvents() { return upcomingEvents; }
+ public void setUpcomingEvents(int upcomingEvents) { this.upcomingEvents = upcomingEvents; }
+
+ public int getTotalMembers() { return totalMembers; }
+ public void setTotalMembers(int totalMembers) { this.totalMembers = totalMembers; }
+
+ public String getAidesDistribuees() { return aidesDistribuees; }
+ public void setAidesDistribuees(String aidesDistribuees) { this.aidesDistribuees = aidesDistribuees; }
+
+ public int getTauxParticipation() { return tauxParticipation; }
+ public void setTauxParticipation(int tauxParticipation) { this.tauxParticipation = tauxParticipation; }
+
+ public int getCotisationsRetard() { return cotisationsRetard; }
+ public void setCotisationsRetard(int cotisationsRetard) { this.cotisationsRetard = cotisationsRetard; }
+
+ public int getAdhesionsExpiration() { return adhesionsExpiration; }
+ public void setAdhesionsExpiration(int adhesionsExpiration) { this.adhesionsExpiration = adhesionsExpiration; }
+
+ public int getDemandesToTraiter() { return demandesToTraiter; }
+ public void setDemandesToTraiter(int demandesToTraiter) { this.demandesToTraiter = demandesToTraiter; }
+
+ public int getTachesFinaliser() { return tachesFinaliser; }
+ public void setTachesFinaliser(int tachesFinaliser) { this.tachesFinaliser = tachesFinaliser; }
+
+ public int getMembresEvolutionPourcent() { return membresEvolutionPourcent; }
+ public void setMembresEvolutionPourcent(int membresEvolutionPourcent) { this.membresEvolutionPourcent = membresEvolutionPourcent; }
+
+ public int getCotisationsEvolutionPourcent() { return cotisationsEvolutionPourcent; }
+ public void setCotisationsEvolutionPourcent(int cotisationsEvolutionPourcent) { this.cotisationsEvolutionPourcent = cotisationsEvolutionPourcent; }
+
+ public String getObjectifCotisations() { return objectifCotisations; }
+ public void setObjectifCotisations(String objectifCotisations) { this.objectifCotisations = objectifCotisations; }
+
+ public int getAidesApprouvees() { return aidesApprouvees; }
+ public void setAidesApprouvees(int aidesApprouvees) { this.aidesApprouvees = aidesApprouvees; }
+
+ public int getMembresParticipants() { return membresParticipants; }
+ public void setMembresParticipants(int membresParticipants) { this.membresParticipants = membresParticipants; }
+
+ public String getPeriodeGraph() { return periodeGraph; }
+ public void setPeriodeGraph(String periodeGraph) { this.periodeGraph = periodeGraph; }
+
+ public String getFiltreActivite() { return filtreActivite; }
+ public void setFiltreActivite(String filtreActivite) { this.filtreActivite = filtreActivite; }
+
+ public int getCotisationsAJour() { return cotisationsAJour; }
+ public void setCotisationsAJour(int cotisationsAJour) { this.cotisationsAJour = cotisationsAJour; }
+
+ public int getCotisationsRetardPourcent() { return cotisationsRetardPourcent; }
+ public void setCotisationsRetardPourcent(int cotisationsRetardPourcent) { this.cotisationsRetardPourcent = cotisationsRetardPourcent; }
+
+ public int getCotisationsImpayees() { return cotisationsImpayees; }
+ public void setCotisationsImpayees(int cotisationsImpayees) { this.cotisationsImpayees = cotisationsImpayees; }
+
+ public int getAdhesionsPendantes() { return adhesionsPendantes; }
+ public void setAdhesionsPendantes(int adhesionsPendantes) { this.adhesionsPendantes = adhesionsPendantes; }
+
+ public int getAidesEnAttente() { return aidesEnAttente; }
+ public void setAidesEnAttente(int aidesEnAttente) { this.aidesEnAttente = aidesEnAttente; }
+
+ public int getEvenementsAPlanifier() { return evenementsAPlanifier; }
+ public void setEvenementsAPlanifier(int evenementsAPlanifier) { this.evenementsAPlanifier = evenementsAPlanifier; }
+
+ public Date getMoisSelectionne() { return moisSelectionne; }
+ public void setMoisSelectionne(Date moisSelectionne) { this.moisSelectionne = moisSelectionne; }
+
+ public String getRecettesMois() { return recettesMois; }
+ public void setRecettesMois(String recettesMois) { this.recettesMois = recettesMois; }
+
+ public String getDepensesMois() { return depensesMois; }
+ public void setDepensesMois(String depensesMois) { this.depensesMois = depensesMois; }
+
+ public String getSoldeMois() { return soldeMois; }
+ public void setSoldeMois(String soldeMois) { this.soldeMois = soldeMois; }
+
+ public String getTresorerie() { return tresorerie; }
+ public void setTresorerie(String tresorerie) { this.tresorerie = tresorerie; }
+
+ public String getCurrentDate() { return currentDate; }
+ public void setCurrentDate(String currentDate) { this.currentDate = currentDate; }
+
+ public int getTauxActivite() { return tauxActivite; }
+ public void setTauxActivite(int tauxActivite) { this.tauxActivite = tauxActivite; }
+
+ public int getTauxObjectifCotisations() { return tauxObjectifCotisations; }
+ public void setTauxObjectifCotisations(int tauxObjectifCotisations) { this.tauxObjectifCotisations = tauxObjectifCotisations; }
+
+ public int getTauxAidesTraitees() { return tauxAidesTraitees; }
+ public void setTauxAidesTraitees(int tauxAidesTraitees) { this.tauxAidesTraitees = tauxAidesTraitees; }
+
+ public int getTauxEngagement() { return tauxEngagement; }
+ public void setTauxEngagement(int tauxEngagement) { this.tauxEngagement = tauxEngagement; }
+
+ public int getTachesCompletees() { return tachesCompletees; }
+ public void setTachesCompletees(int tachesCompletees) { this.tachesCompletees = tachesCompletees; }
+
+ public boolean isHasAlerts() { return hasAlerts; }
+ public void setHasAlerts(boolean hasAlerts) { this.hasAlerts = hasAlerts; }
+
+ // Méthodes pour les activités récentes
+ public List getRecentActivities() {
+ List activities = new ArrayList<>();
+
+ activities.add(new Activity(
+ LocalDateTime.now().minusHours(2),
+ "COTISATION",
+ "success",
+ "pi pi-check-circle",
+ "Paiement cotisation validé",
+ "Cotisation de Fatou Sow pour juillet 2024",
+ "25,000",
+ "Fatou Sow",
+ "Membre"
+ ));
+
+ activities.add(new Activity(
+ LocalDateTime.now().minusHours(5),
+ "ADHESION",
+ "info",
+ "pi pi-user-plus",
+ "Nouvelle demande d'adhésion",
+ "Demande soumise par Moussa Ba",
+ null,
+ "Moussa Ba",
+ "Candidat"
+ ));
+
+ activities.add(new Activity(
+ LocalDateTime.now().minusHours(8),
+ "AIDE",
+ "warning",
+ "pi pi-heart",
+ "Demande d'aide en traitement",
+ "Aide médicale pour famille Ndiaye",
+ "150,000",
+ "Aminata Ndiaye",
+ "Membre"
+ ));
+
+ activities.add(new Activity(
+ LocalDateTime.now().minusDays(1),
+ "EVENEMENT",
+ "info",
+ "pi pi-calendar",
+ "Événement planifié",
+ "Assemblée générale mensuelle programmée",
+ null,
+ "Admin",
+ "Administrateur"
+ ));
+
+ activities.add(new Activity(
+ LocalDateTime.now().minusDays(1).minusHours(3),
+ "COTISATION",
+ "danger",
+ "pi pi-exclamation-triangle",
+ "Relance envoyée",
+ "Relance automatique pour cotisation en retard",
+ null,
+ "Système",
+ "Automatique"
+ ));
+
+ return activities;
+ }
+
+ // Actions de navigation
+ public String redirectToNewMember() {
+ return "/pages/secure/membre/inscription?faces-redirect=true";
+ }
+
+ public String redirectToCotisation() {
+ return "/pages/secure/cotisation/paiement?faces-redirect=true";
+ }
+
+ public String redirectToEvenement() {
+ return "/pages/secure/evenement/creation?faces-redirect=true";
+ }
+
+ public String redirectToAdhesionValidation() {
+ return "/pages/secure/adhesion/validation?faces-redirect=true";
+ }
+
+ public String redirectToRelances() {
+ return "/pages/secure/cotisation/relances?faces-redirect=true";
+ }
+
+ public String redirectToAidesTraitement() {
+ return "/pages/secure/aide/traitement?faces-redirect=true";
+ }
+
+ public String redirectToEvenementPlanning() {
+ return "/pages/secure/evenement/gestion?faces-redirect=true";
+ }
+
+ public void generateRapport() {
+ // Logique de génération de rapport
+ }
+
+ public void exportFinancialReport() {
+ // Logique d'export du rapport financier
+ }
+
+ public void onMoisChange() {
+ // Logique de mise à jour lors du changement de mois
+ }
+
+ // Classe interne pour les activités enrichie
+ public static class Activity implements Serializable {
+ private LocalDateTime date;
+ private String type;
+ private String severity;
+ private String icon;
+ private String titre;
+ private String description;
+ private String montant;
+ private String userNom;
+ private String userRole;
+
+ public Activity(LocalDateTime date, String type, String severity, String icon,
+ String titre, String description, String montant, String userNom, String userRole) {
+ this.date = date;
+ this.type = type;
+ this.severity = severity;
+ this.icon = icon;
+ this.titre = titre;
+ this.description = description;
+ this.montant = montant;
+ this.userNom = userNom;
+ this.userRole = userRole;
+ }
+
+ // Getters et setters
+ public LocalDateTime getDate() { return date; }
+ public void setDate(LocalDateTime date) { this.date = date; }
+
+ public String getType() { return type; }
+ public void setType(String type) { this.type = type; }
+
+ public String getSeverity() { return severity; }
+ public void setSeverity(String severity) { this.severity = severity; }
+
+ public String getIcon() { return icon; }
+ public void setIcon(String icon) { this.icon = icon; }
+
+ public String getTitre() { return titre; }
+ public void setTitre(String titre) { this.titre = titre; }
+
+ public String getDescription() { return description; }
+ public void setDescription(String description) { this.description = description; }
+
+ public String getMontant() { return montant; }
+ public void setMontant(String montant) { this.montant = montant; }
+
+ public String getUserNom() { return userNom; }
+ public void setUserNom(String userNom) { this.userNom = userNom; }
+
+ public String getUserRole() { return userRole; }
+ public void setUserRole(String userRole) { this.userRole = userRole; }
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/DemandesAideBean.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/DemandesAideBean.java
new file mode 100644
index 0000000..4fe591a
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/DemandesAideBean.java
@@ -0,0 +1,638 @@
+package dev.lions.unionflow.client.view;
+
+import jakarta.enterprise.context.SessionScoped;
+import jakarta.inject.Named;
+import jakarta.annotation.PostConstruct;
+import java.io.Serializable;
+import java.time.LocalDate;
+import java.time.format.DateTimeFormatter;
+import java.time.temporal.ChronoUnit;
+import java.util.ArrayList;
+import java.util.List;
+import java.util.stream.Collectors;
+import java.math.BigDecimal;
+
+@Named("demandesAideBean")
+@SessionScoped
+public class DemandesAideBean implements Serializable {
+
+ private static final long serialVersionUID = 1L;
+
+ private List toutesLesDemandes;
+ private List demandesFiltrees;
+ private List demandesSelectionnees;
+ private List demandesPrioritaires;
+ private List etapesWorkflow;
+ private DemandeAide demandeSelectionnee;
+ private NouvelleDemande nouvelleDemande;
+ private Filtres filtres;
+ private StatistiquesDemandes statistiques;
+
+ @PostConstruct
+ public void init() {
+ initializeFiltres();
+ initializeStatistiques();
+ initializeDemandes();
+ initializeNouvelleDemande();
+ initializeDemandesPrioritaires();
+ initializeEtapesWorkflow();
+ appliquerFiltres();
+ }
+
+ private void initializeFiltres() {
+ filtres = new Filtres();
+ demandesSelectionnees = new ArrayList<>();
+ }
+
+ private void initializeStatistiques() {
+ statistiques = new StatistiquesDemandes();
+ statistiques.setTotalDemandes(156);
+ statistiques.setDemandesEnAttente(23);
+ statistiques.setDemandesApprouvees(89);
+ statistiques.setMontantTotalAide("12 850 000 FCFA");
+ }
+
+ private void initializeEtapesWorkflow() {
+ etapesWorkflow = new ArrayList<>();
+
+ EtapeWorkflow enAttente = new EtapeWorkflow();
+ enAttente.setLibelle("En Attente");
+ enAttente.setIcon("pi-clock");
+ enAttente.setCouleur("orange-500");
+ enAttente.setNombre(23);
+ etapesWorkflow.add(enAttente);
+
+ EtapeWorkflow evaluation = new EtapeWorkflow();
+ evaluation.setLibelle("Évaluation");
+ evaluation.setIcon("pi-search");
+ evaluation.setCouleur("blue-500");
+ evaluation.setNombre(15);
+ etapesWorkflow.add(evaluation);
+
+ EtapeWorkflow visite = new EtapeWorkflow();
+ visite.setLibelle("Visite");
+ visite.setIcon("pi-home");
+ visite.setCouleur("purple-500");
+ visite.setNombre(8);
+ etapesWorkflow.add(visite);
+
+ EtapeWorkflow decision = new EtapeWorkflow();
+ decision.setLibelle("Décision");
+ decision.setIcon("pi-check-circle");
+ decision.setCouleur("yellow-500");
+ decision.setNombre(12);
+ etapesWorkflow.add(decision);
+
+ EtapeWorkflow versement = new EtapeWorkflow();
+ versement.setLibelle("Versement");
+ versement.setIcon("pi-dollar");
+ versement.setCouleur("green-500");
+ versement.setNombre(6);
+ etapesWorkflow.add(versement);
+
+ EtapeWorkflow suivi = new EtapeWorkflow();
+ suivi.setLibelle("Suivi");
+ suivi.setIcon("pi-chart-line");
+ suivi.setCouleur("indigo-500");
+ suivi.setNombre(4);
+ etapesWorkflow.add(suivi);
+ }
+
+ private void initializeDemandes() {
+ toutesLesDemandes = new ArrayList<>();
+
+ String[] demandeurs = {
+ "Jean Kouassi", "Marie Traoré", "Ahmed Diallo", "Fatou Sanogo", "Paul Ouattara",
+ "Aissata Koné", "Ibrahim Touré", "Aminata Bakayoko", "Yves Koffi", "Mariam Coulibaly",
+ "Seydou Cissé", "Adjoa Mensah", "Kwame Asante", "Ama Gyamfi", "Kofi Adjei",
+ "Nana Akoto", "Akosua Boateng", "Emmanuel Ofori", "Joyce Owusu", "Stephen Asamoah"
+ };
+
+ String[] types = {
+ "AIDE_MEDICALE", "AIDE_ALIMENTAIRE", "AIDE_EDUCATIVE", "AIDE_LOGEMENT", "AIDE_URGENCE"
+ };
+
+ String[] statuts = {
+ "EN_ATTENTE", "EN_EVALUATION", "APPROUVEE", "REJETEE", "EN_COURS", "TERMINEE"
+ };
+
+ String[] urgences = {
+ "FAIBLE", "NORMALE", "ELEVEE", "CRITIQUE"
+ };
+
+ String[] localisations = {
+ "Zone Urbaine Centre", "Quartier Résidentiel Nord", "Zone Rurale Sud",
+ "Quartier Populaire Est", "Zone Industrielle Ouest", "Centre-Ville",
+ "Banlieue Nord", "Périphérie Sud", "Zone Commerciale", "Quartier Administratif"
+ };
+
+ String[] motifs = {
+ "Soins médicaux d'urgence", "Aide alimentaire famille nombreuse", "Frais de scolarité",
+ "Réparation logement suite inondation", "Urgence médicale enfant", "Soutien alimentaire mensuel",
+ "Achat fournitures scolaires", "Paiement loyer en retard", "Intervention chirurgicale",
+ "Aide nutritionnelle nourrisson", "Formation professionnelle", "Réhabilitation habitat",
+ "Traitement médical chronique", "Complément alimentaire", "Équipement scolaire"
+ };
+
+ for (int i = 0; i < 50; i++) {
+ DemandeAide demande = new DemandeAide();
+ demande.setId((long) (i + 1));
+ demande.setDemandeur(demandeurs[i % demandeurs.length]);
+ demande.setTelephone("77 123 45 " + String.format("%02d", (i % 99) + 1));
+ demande.setEmail(demandeurs[i % demandeurs.length].toLowerCase().replace(" ", ".") + "@email.com");
+ demande.setType(types[i % types.length]);
+ demande.setStatut(statuts[i % statuts.length]);
+ demande.setUrgence(urgences[i % urgences.length]);
+ demande.setLocalisation(localisations[i % localisations.length]);
+ demande.setMotif(motifs[i % motifs.length]);
+ demande.setDescription("Description détaillée pour " + motifs[i % motifs.length] + ". Situation nécessitant une évaluation approfondie.");
+
+ // Montants
+ BigDecimal montantBase = new BigDecimal(50000 + (i * 15000));
+ demande.setMontantDemande(montantBase);
+
+ if (demande.getStatut().equals("APPROUVEE") || demande.getStatut().equals("EN_COURS") || demande.getStatut().equals("TERMINEE")) {
+ demande.setMontantAccorde(montantBase.multiply(new BigDecimal("0.8")));
+ }
+
+ // Dates
+ demande.setDateDemande(LocalDate.now().minusDays(i + 1));
+ if (i % 4 == 0) {
+ demande.setDateLimite(LocalDate.now().plusDays(7 + (i % 14)));
+ }
+
+ // Responsable de traitement
+ if (!demande.getStatut().equals("EN_ATTENTE")) {
+ String[] responsables = {"Sarah Mensah", "David Konaté", "Grace Asante", "Michel Diallo", "Rita Kouassi"};
+ demande.setResponsableTraitement(responsables[i % responsables.length]);
+ }
+
+ toutesLesDemandes.add(demande);
+ }
+ }
+
+ private void initializeDemandesPrioritaires() {
+ demandesPrioritaires = toutesLesDemandes.stream()
+ .filter(d -> d.getUrgence().equals("CRITIQUE") || d.getUrgence().equals("ELEVEE"))
+ .filter(d -> !d.getStatut().equals("TERMINEE") && !d.getStatut().equals("REJETEE"))
+ .sorted((d1, d2) -> d1.getDateDemande().compareTo(d2.getDateDemande()))
+ .limit(6)
+ .collect(Collectors.toList());
+ }
+
+ private void initializeNouvelleDemande() {
+ nouvelleDemande = new NouvelleDemande();
+ nouvelleDemande.setUrgence("NORMALE");
+ nouvelleDemande.setDateLimite(LocalDate.now().plusWeeks(2));
+ }
+
+ private void appliquerFiltres() {
+ demandesFiltrees = toutesLesDemandes.stream()
+ .filter(this::appliquerFiltre)
+ .collect(Collectors.toList());
+ }
+
+ private boolean appliquerFiltre(DemandeAide demande) {
+ if (filtres.getDemandeur() != null && !filtres.getDemandeur().trim().isEmpty()) {
+ if (!demande.getDemandeur().toLowerCase().contains(filtres.getDemandeur().toLowerCase())) {
+ return false;
+ }
+ }
+
+ if (filtres.getType() != null && !filtres.getType().trim().isEmpty()) {
+ if (!demande.getType().equals(filtres.getType())) {
+ return false;
+ }
+ }
+
+ if (filtres.getStatut() != null && !filtres.getStatut().trim().isEmpty()) {
+ if (!demande.getStatut().equals(filtres.getStatut())) {
+ return false;
+ }
+ }
+
+ if (filtres.getUrgence() != null && !filtres.getUrgence().trim().isEmpty()) {
+ if (!demande.getUrgence().equals(filtres.getUrgence())) {
+ return false;
+ }
+ }
+
+ if (filtres.getLocalisation() != null && !filtres.getLocalisation().trim().isEmpty()) {
+ if (!demande.getLocalisation().toLowerCase().contains(filtres.getLocalisation().toLowerCase())) {
+ return false;
+ }
+ }
+
+ if (filtres.getDateDebut() != null) {
+ if (demande.getDateDemande().isBefore(filtres.getDateDebut())) {
+ return false;
+ }
+ }
+
+ if (filtres.getDateFin() != null) {
+ if (demande.getDateDemande().isAfter(filtres.getDateFin())) {
+ return false;
+ }
+ }
+
+ return true;
+ }
+
+ // Actions
+ public void rechercher() {
+ appliquerFiltres();
+ }
+
+ public void reinitialiserFiltres() {
+ filtres = new Filtres();
+ appliquerFiltres();
+ }
+
+ public void creerDemande() {
+ DemandeAide nouvelleDem = new DemandeAide();
+ nouvelleDem.setId((long) (toutesLesDemandes.size() + 1));
+ nouvelleDem.setDemandeur(nouvelleDemande.getDemandeur());
+ nouvelleDem.setTelephone(nouvelleDemande.getTelephone());
+ nouvelleDem.setEmail(nouvelleDemande.getEmail());
+ nouvelleDem.setType(nouvelleDemande.getType());
+ nouvelleDem.setLocalisation(nouvelleDemande.getLocalisation());
+ nouvelleDem.setMontantDemande(nouvelleDemande.getMontantDemande());
+ nouvelleDem.setUrgence(nouvelleDemande.getUrgence());
+ nouvelleDem.setDateLimite(nouvelleDemande.getDateLimite());
+ nouvelleDem.setMotif(nouvelleDemande.getMotif());
+ nouvelleDem.setDescription(nouvelleDemande.getDescription());
+ nouvelleDem.setStatut("EN_ATTENTE");
+ nouvelleDem.setDateDemande(LocalDate.now());
+
+ toutesLesDemandes.add(nouvelleDem);
+ appliquerFiltres();
+ initializeDemandesPrioritaires();
+
+ System.out.println("Nouvelle demande d'aide créée pour: " + nouvelleDem.getDemandeur());
+ initializeNouvelleDemande();
+ }
+
+ public void approuverDemande() {
+ if (demandeSelectionnee != null) {
+ demandeSelectionnee.setStatut("APPROUVEE");
+ if (demandeSelectionnee.getMontantAccorde() == null) {
+ demandeSelectionnee.setMontantAccorde(demandeSelectionnee.getMontantDemande().multiply(new BigDecimal("0.8")));
+ }
+ System.out.println("Demande approuvée pour: " + demandeSelectionnee.getDemandeur());
+ appliquerFiltres();
+ initializeDemandesPrioritaires();
+ }
+ }
+
+ public void rejeterDemande() {
+ if (demandeSelectionnee != null) {
+ demandeSelectionnee.setStatut("REJETEE");
+ System.out.println("Demande rejetée pour: " + demandeSelectionnee.getDemandeur());
+ appliquerFiltres();
+ initializeDemandesPrioritaires();
+ }
+ }
+
+ public String voirHistorique() {
+ return "/pages/admin/demandes/historique?id=" + demandeSelectionnee.getId() + "&faces-redirect=true";
+ }
+
+ public void envoyerNotification() {
+ System.out.println("Notification envoyée pour la demande de: " + demandeSelectionnee.getDemandeur());
+ }
+
+ public void dupliquerDemande() {
+ if (demandeSelectionnee != null) {
+ DemandeAide copie = new DemandeAide();
+ copie.setId((long) (toutesLesDemandes.size() + 1));
+ copie.setDemandeur(demandeSelectionnee.getDemandeur());
+ copie.setTelephone(demandeSelectionnee.getTelephone());
+ copie.setEmail(demandeSelectionnee.getEmail());
+ copie.setType(demandeSelectionnee.getType());
+ copie.setLocalisation(demandeSelectionnee.getLocalisation());
+ copie.setMontantDemande(demandeSelectionnee.getMontantDemande());
+ copie.setUrgence(demandeSelectionnee.getUrgence());
+ copie.setMotif(demandeSelectionnee.getMotif() + " (Copie)");
+ copie.setDescription(demandeSelectionnee.getDescription());
+ copie.setStatut("EN_ATTENTE");
+ copie.setDateDemande(LocalDate.now());
+
+ toutesLesDemandes.add(copie);
+ appliquerFiltres();
+ System.out.println("Demande dupliquée pour: " + copie.getDemandeur());
+ }
+ }
+
+ public void exporterDemandes() {
+ System.out.println("Export de " + demandesFiltrees.size() + " demandes d'aide");
+ }
+
+ // Getters et Setters
+ public List getToutesLesDemandes() { return toutesLesDemandes; }
+ public void setToutesLesDemandes(List toutesLesDemandes) { this.toutesLesDemandes = toutesLesDemandes; }
+
+ public List getDemandesFiltrees() { return demandesFiltrees; }
+ public void setDemandesFiltrees(List demandesFiltrees) { this.demandesFiltrees = demandesFiltrees; }
+
+ public List getDemandesSelectionnees() { return demandesSelectionnees; }
+ public void setDemandesSelectionnees(List demandesSelectionnees) { this.demandesSelectionnees = demandesSelectionnees; }
+
+ public List getDemandesPrioritaires() { return demandesPrioritaires; }
+ public void setDemandesPrioritaires(List demandesPrioritaires) { this.demandesPrioritaires = demandesPrioritaires; }
+
+ public List getEtapesWorkflow() { return etapesWorkflow; }
+ public void setEtapesWorkflow(List etapesWorkflow) { this.etapesWorkflow = etapesWorkflow; }
+
+ public DemandeAide getDemandeSelectionnee() { return demandeSelectionnee; }
+ public void setDemandeSelectionnee(DemandeAide demandeSelectionnee) { this.demandeSelectionnee = demandeSelectionnee; }
+
+ public NouvelleDemande getNouvelleDemande() { return nouvelleDemande; }
+ public void setNouvelleDemande(NouvelleDemande nouvelleDemande) { this.nouvelleDemande = nouvelleDemande; }
+
+ public Filtres getFiltres() { return filtres; }
+ public void setFiltres(Filtres filtres) { this.filtres = filtres; }
+
+ public StatistiquesDemandes getStatistiques() { return statistiques; }
+ public void setStatistiques(StatistiquesDemandes statistiques) { this.statistiques = statistiques; }
+
+ // Classes internes
+ public static class DemandeAide {
+ private Long id;
+ private String demandeur;
+ private String telephone;
+ private String email;
+ private String type;
+ private String statut;
+ private String urgence;
+ private String localisation;
+ private String motif;
+ private String description;
+ private BigDecimal montantDemande;
+ private BigDecimal montantAccorde;
+ private LocalDate dateDemande;
+ private LocalDate dateLimite;
+ private String responsableTraitement;
+
+ // Getters et setters
+ public Long getId() { return id; }
+ public void setId(Long id) { this.id = id; }
+
+ public String getDemandeur() { return demandeur; }
+ public void setDemandeur(String demandeur) { this.demandeur = demandeur; }
+
+ public String getTelephone() { return telephone; }
+ public void setTelephone(String telephone) { this.telephone = telephone; }
+
+ public String getEmail() { return email; }
+ public void setEmail(String email) { this.email = email; }
+
+ public String getType() { return type; }
+ public void setType(String type) { this.type = type; }
+
+ public String getStatut() { return statut; }
+ public void setStatut(String statut) { this.statut = statut; }
+
+ public String getUrgence() { return urgence; }
+ public void setUrgence(String urgence) { this.urgence = urgence; }
+
+ public String getLocalisation() { return localisation; }
+ public void setLocalisation(String localisation) { this.localisation = localisation; }
+
+ public String getMotif() { return motif; }
+ public void setMotif(String motif) { this.motif = motif; }
+
+ public String getDescription() { return description; }
+ public void setDescription(String description) { this.description = description; }
+
+ public BigDecimal getMontantDemande() { return montantDemande; }
+ public void setMontantDemande(BigDecimal montantDemande) { this.montantDemande = montantDemande; }
+
+ public BigDecimal getMontantAccorde() { return montantAccorde; }
+ public void setMontantAccorde(BigDecimal montantAccorde) { this.montantAccorde = montantAccorde; }
+
+ public LocalDate getDateDemande() { return dateDemande; }
+ public void setDateDemande(LocalDate dateDemande) { this.dateDemande = dateDemande; }
+
+ public LocalDate getDateLimite() { return dateLimite; }
+ public void setDateLimite(LocalDate dateLimite) { this.dateLimite = dateLimite; }
+
+ public String getResponsableTraitement() { return responsableTraitement; }
+ public void setResponsableTraitement(String responsableTraitement) { this.responsableTraitement = responsableTraitement; }
+
+ // Propriétés dérivées
+ public String getTypeLibelle() {
+ return switch (type) {
+ case "AIDE_MEDICALE" -> "Aide Médicale";
+ case "AIDE_ALIMENTAIRE" -> "Aide Alimentaire";
+ case "AIDE_EDUCATIVE" -> "Aide Éducative";
+ case "AIDE_LOGEMENT" -> "Aide Logement";
+ case "AIDE_URGENCE" -> "Aide d'Urgence";
+ default -> type;
+ };
+ }
+
+ public String getTypeSeverity() {
+ return switch (type) {
+ case "AIDE_MEDICALE" -> "danger";
+ case "AIDE_ALIMENTAIRE" -> "warning";
+ case "AIDE_EDUCATIVE" -> "info";
+ case "AIDE_LOGEMENT" -> "secondary";
+ case "AIDE_URGENCE" -> "primary";
+ default -> "primary";
+ };
+ }
+
+ public String getTypeIcon() {
+ return switch (type) {
+ case "AIDE_MEDICALE" -> "pi-heart";
+ case "AIDE_ALIMENTAIRE" -> "pi-shopping-cart";
+ case "AIDE_EDUCATIVE" -> "pi-book";
+ case "AIDE_LOGEMENT" -> "pi-home";
+ case "AIDE_URGENCE" -> "pi-exclamation-triangle";
+ default -> "pi-question";
+ };
+ }
+
+ public String getStatutLibelle() {
+ return switch (statut) {
+ case "EN_ATTENTE" -> "En Attente";
+ case "EN_EVALUATION" -> "En Évaluation";
+ case "APPROUVEE" -> "Approuvée";
+ case "REJETEE" -> "Rejetée";
+ case "EN_COURS" -> "En Cours";
+ case "TERMINEE" -> "Terminée";
+ default -> statut;
+ };
+ }
+
+ public String getStatutSeverity() {
+ return switch (statut) {
+ case "EN_ATTENTE" -> "warning";
+ case "EN_EVALUATION" -> "info";
+ case "APPROUVEE" -> "success";
+ case "REJETEE" -> "danger";
+ case "EN_COURS" -> "primary";
+ case "TERMINEE" -> "secondary";
+ default -> "secondary";
+ };
+ }
+
+ public String getStatutIcon() {
+ return switch (statut) {
+ case "EN_ATTENTE" -> "pi-clock";
+ case "EN_EVALUATION" -> "pi-search";
+ case "APPROUVEE" -> "pi-check";
+ case "REJETEE" -> "pi-times";
+ case "EN_COURS" -> "pi-play";
+ case "TERMINEE" -> "pi-check-circle";
+ default -> "pi-circle";
+ };
+ }
+
+ public String getUrgenceSeverity() {
+ return switch (urgence) {
+ case "FAIBLE" -> "secondary";
+ case "NORMALE" -> "info";
+ case "ELEVEE" -> "warning";
+ case "CRITIQUE" -> "danger";
+ default -> "primary";
+ };
+ }
+
+ public String getDateDemandeFormatee() {
+ if (dateDemande == null) return "";
+ return dateDemande.format(DateTimeFormatter.ofPattern("dd/MM/yyyy"));
+ }
+
+ public String getMontantDemandeFormatte() {
+ if (montantDemande == null) return "";
+ return String.format("%,.0f FCFA", montantDemande);
+ }
+
+ public String getMontantAccordeFormatte() {
+ if (montantAccorde == null) return "";
+ return String.format("%,.0f FCFA", montantAccorde);
+ }
+
+ public long getJoursDepuisDemande() {
+ if (dateDemande == null) return 0;
+ return ChronoUnit.DAYS.between(dateDemande, LocalDate.now());
+ }
+ }
+
+ public static class NouvelleDemande {
+ private String demandeur;
+ private String telephone;
+ private String email;
+ private String type;
+ private String localisation;
+ private BigDecimal montantDemande;
+ private String urgence;
+ private LocalDate dateLimite;
+ private String motif;
+ private String description;
+
+ // Getters et setters
+ public String getDemandeur() { return demandeur; }
+ public void setDemandeur(String demandeur) { this.demandeur = demandeur; }
+
+ public String getTelephone() { return telephone; }
+ public void setTelephone(String telephone) { this.telephone = telephone; }
+
+ public String getEmail() { return email; }
+ public void setEmail(String email) { this.email = email; }
+
+ public String getType() { return type; }
+ public void setType(String type) { this.type = type; }
+
+ public String getLocalisation() { return localisation; }
+ public void setLocalisation(String localisation) { this.localisation = localisation; }
+
+ public BigDecimal getMontantDemande() { return montantDemande; }
+ public void setMontantDemande(BigDecimal montantDemande) { this.montantDemande = montantDemande; }
+
+ public String getUrgence() { return urgence; }
+ public void setUrgence(String urgence) { this.urgence = urgence; }
+
+ public LocalDate getDateLimite() { return dateLimite; }
+ public void setDateLimite(LocalDate dateLimite) { this.dateLimite = dateLimite; }
+
+ public String getMotif() { return motif; }
+ public void setMotif(String motif) { this.motif = motif; }
+
+ public String getDescription() { return description; }
+ public void setDescription(String description) { this.description = description; }
+ }
+
+ public static class Filtres {
+ private String demandeur;
+ private String type;
+ private String statut;
+ private String urgence;
+ private String localisation;
+ private LocalDate dateDebut;
+ private LocalDate dateFin;
+
+ // Getters et setters
+ public String getDemandeur() { return demandeur; }
+ public void setDemandeur(String demandeur) { this.demandeur = demandeur; }
+
+ public String getType() { return type; }
+ public void setType(String type) { this.type = type; }
+
+ public String getStatut() { return statut; }
+ public void setStatut(String statut) { this.statut = statut; }
+
+ public String getUrgence() { return urgence; }
+ public void setUrgence(String urgence) { this.urgence = urgence; }
+
+ public String getLocalisation() { return localisation; }
+ public void setLocalisation(String localisation) { this.localisation = localisation; }
+
+ public LocalDate getDateDebut() { return dateDebut; }
+ public void setDateDebut(LocalDate dateDebut) { this.dateDebut = dateDebut; }
+
+ public LocalDate getDateFin() { return dateFin; }
+ public void setDateFin(LocalDate dateFin) { this.dateFin = dateFin; }
+ }
+
+ public static class StatistiquesDemandes {
+ private int totalDemandes;
+ private int demandesEnAttente;
+ private int demandesApprouvees;
+ private String montantTotalAide;
+
+ // Getters et setters
+ public int getTotalDemandes() { return totalDemandes; }
+ public void setTotalDemandes(int totalDemandes) { this.totalDemandes = totalDemandes; }
+
+ public int getDemandesEnAttente() { return demandesEnAttente; }
+ public void setDemandesEnAttente(int demandesEnAttente) { this.demandesEnAttente = demandesEnAttente; }
+
+ public int getDemandesApprouvees() { return demandesApprouvees; }
+ public void setDemandesApprouvees(int demandesApprouvees) { this.demandesApprouvees = demandesApprouvees; }
+
+ public String getMontantTotalAide() { return montantTotalAide; }
+ public void setMontantTotalAide(String montantTotalAide) { this.montantTotalAide = montantTotalAide; }
+ }
+
+ public static class EtapeWorkflow {
+ private String libelle;
+ private String icon;
+ private String couleur;
+ private int nombre;
+
+ // Getters et setters
+ public String getLibelle() { return libelle; }
+ public void setLibelle(String libelle) { this.libelle = libelle; }
+
+ public String getIcon() { return icon; }
+ public void setIcon(String icon) { this.icon = icon; }
+
+ public String getCouleur() { return couleur; }
+ public void setCouleur(String couleur) { this.couleur = couleur; }
+
+ public int getNombre() { return nombre; }
+ public void setNombre(int nombre) { this.nombre = nombre; }
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/DemandesBean.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/DemandesBean.java
new file mode 100644
index 0000000..a4e4d60
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/DemandesBean.java
@@ -0,0 +1,463 @@
+package dev.lions.unionflow.client.view;
+
+import jakarta.enterprise.context.SessionScoped;
+import jakarta.inject.Named;
+import jakarta.annotation.PostConstruct;
+import java.io.Serializable;
+import java.time.LocalDate;
+import java.time.LocalDateTime;
+import java.time.format.DateTimeFormatter;
+import java.time.temporal.ChronoUnit;
+import java.util.ArrayList;
+import java.util.List;
+import java.util.stream.Collectors;
+
+@Named("demandeBean")
+@SessionScoped
+public class DemandesBean implements Serializable {
+
+ private static final long serialVersionUID = 1L;
+
+ private List demandes;
+ private List selectedDemandes;
+ private List demandesUrgentes;
+ private List dernieresDemandes;
+ private List gestionnairesDisponibles;
+ private Membre membreDemandeur;
+ private NouvelleDemande nouvelleDemande;
+ private Demande demandeSelectionnee;
+
+ // Filtres
+ private String searchFilter;
+ private String statutFilter;
+ private String typeFilter;
+ private String prioriteFilter;
+ private LocalDate dateFilter;
+
+ // Assignation en lot
+ private Long gestionnaireAssignation;
+ private String commentaireAssignation;
+
+ // Statistiques
+ private int enAttente = 12;
+ private int urgentes = 5;
+ private int traitees = 143;
+ private int delaiMoyenTraitement = 3;
+
+ @PostConstruct
+ public void init() {
+ initializeDemandes();
+ initializeGestionnaires();
+ initializeNouvelleDemande();
+ selectedDemandes = new ArrayList<>();
+ }
+
+ private void initializeDemandes() {
+ demandes = new ArrayList<>();
+
+ String[] objets = {
+ "Demande d'aide financière urgente", "Certificat de membership",
+ "Mutation vers club Dakar", "Réclamation cotisation",
+ "Aide médicale famille", "Certificat de bonne conduite"
+ };
+
+ String[] types = {"AIDE_FINANCIERE", "CERTIFICAT", "MUTATION", "RECLAMATION", "AIDE_FINANCIERE", "CERTIFICAT"};
+ String[] statuts = {"EN_ATTENTE", "EN_COURS", "APPROUVEE", "EN_ATTENTE", "URGENTE", "EN_COURS"};
+ String[] priorites = {"URGENTE", "NORMALE", "NORMALE", "BASSE", "URGENTE", "NORMALE"};
+ String[] demandeurs = {"Marie Kouassi", "Paul Traoré", "Fatou Sanogo", "Jean Ouattara", "Aissata Koné", "Ibrahim Touré"};
+
+ for (int i = 0; i < objets.length; i++) {
+ Demande demande = new Demande();
+ demande.setId((long) (i + 1));
+ demande.setReference("DEM-2024-" + String.format("%04d", i + 1));
+ demande.setObjet(objets[i]);
+ demande.setType(types[i]);
+ demande.setStatut(statuts[i]);
+ demande.setPriorite(priorites[i]);
+ demande.setNomDemandeur(demandeurs[i]);
+ demande.setNumeroMembre("M" + String.format("%06d", 1000 + i));
+ demande.setTelephoneDemandeur("+225 07 " + String.format("%02d", 10 + i) + " " + String.format("%02d", 20 + i) + " " + String.format("%02d", 30 + i));
+ demande.setDateDepot(LocalDate.now().minusDays(i * 2));
+ demande.setDateEcheance(LocalDate.now().plusDays(7 + i));
+ demande.setHeureDepot(LocalDateTime.now().minusHours(i * 3).format(DateTimeFormatter.ofPattern("HH:mm")));
+ if (i % 3 != 0) demande.setAssigneA("Gestionnaire " + (i % 3 + 1));
+ demandes.add(demande);
+ }
+
+ // Initialiser les sous-listes
+ demandesUrgentes = demandes.stream()
+ .filter(d -> "URGENTE".equals(d.getPriorite()) || "EN_ATTENTE".equals(d.getStatut()))
+ .limit(3)
+ .collect(Collectors.toList());
+
+ dernieresDemandes = demandes.stream()
+ .limit(4)
+ .collect(Collectors.toList());
+ }
+
+ private void initializeGestionnaires() {
+ gestionnairesDisponibles = new ArrayList<>();
+ gestionnairesDisponibles.add(new Gestionnaire(1L, "Marie Gestionnaire"));
+ gestionnairesDisponibles.add(new Gestionnaire(2L, "Paul Superviseur"));
+ gestionnairesDisponibles.add(new Gestionnaire(3L, "Fatou Responsable"));
+ }
+
+ private void initializeNouvelleDemande() {
+ nouvelleDemande = new NouvelleDemande();
+ nouvelleDemande.setPriorite("NORMALE");
+ nouvelleDemande.setDateEcheance(LocalDate.now().plusWeeks(2));
+ }
+
+ public List rechercherMembres(String query) {
+ List resultats = new ArrayList<>();
+
+ String[] noms = {"Marie Kouassi", "Paul Traoré", "Fatou Sanogo", "Jean Ouattara", "Aissata Koné"};
+ for (int i = 0; i < noms.length; i++) {
+ if (noms[i].toLowerCase().contains(query.toLowerCase())) {
+ Membre membre = new Membre();
+ membre.setId((long) (i + 1));
+ membre.setNomComplet(noms[i]);
+ membre.setNumeroMembre("M" + String.format("%06d", 1000 + i));
+ resultats.add(membre);
+ }
+ }
+
+ return resultats;
+ }
+
+ // Actions
+ public void voirDemande(Demande demande) {
+ this.demandeSelectionnee = demande;
+ System.out.println("Voir demande: " + demande.getObjet());
+ }
+
+ public void traiterDemande(Demande demande) {
+ demande.setStatut("EN_COURS");
+ System.out.println("Traitement demande: " + demande.getObjet());
+ }
+
+ public void approuverDemande(Demande demande) {
+ demande.setStatut("APPROUVEE");
+ System.out.println("Demande approuvée: " + demande.getObjet());
+ }
+
+ public void rejeterDemande(Demande demande) {
+ demande.setStatut("REJETEE");
+ System.out.println("Demande rejetée: " + demande.getObjet());
+ }
+
+ public void assignerDemande(Demande demande) {
+ System.out.println("Assigner demande: " + demande.getObjet());
+ }
+
+ public void voirPiecesJointes(Demande demande) {
+ System.out.println("Voir pièces jointes: " + demande.getObjet());
+ }
+
+ public void creerDemande() {
+ System.out.println("Créer nouvelle demande: " + nouvelleDemande.getObjet());
+ initializeNouvelleDemande();
+ }
+
+ public void effectuerAssignationLot() {
+ System.out.println("Assignation en lot à gestionnaire ID: " + gestionnaireAssignation);
+ }
+
+ public void marquerTraitees() {
+ selectedDemandes.forEach(d -> d.setStatut("TRAITEE"));
+ System.out.println("Marquées comme traitées: " + selectedDemandes.size());
+ }
+
+ public void exporterSelection() {
+ System.out.println("Export de " + selectedDemandes.size() + " demandes");
+ }
+
+ public void exporterDemandes() {
+ System.out.println("Export de toutes les demandes");
+ }
+
+ public void actualiser() {
+ System.out.println("Actualisation des données");
+ }
+
+ public void filtrerUrgentes() {
+ System.out.println("Filtrer les demandes urgentes");
+ }
+
+ // Getters et Setters
+ public List getDemandes() { return demandes; }
+ public void setDemandes(List demandes) { this.demandes = demandes; }
+
+ public List getSelectedDemandes() { return selectedDemandes; }
+ public void setSelectedDemandes(List selectedDemandes) { this.selectedDemandes = selectedDemandes; }
+
+ public List getDemandesUrgentes() { return demandesUrgentes; }
+ public void setDemandesUrgentes(List demandesUrgentes) { this.demandesUrgentes = demandesUrgentes; }
+
+ public List getDernieresDemandes() { return dernieresDemandes; }
+ public void setDernieresDemandes(List dernieresDemandes) { this.dernieresDemandes = dernieresDemandes; }
+
+ public List getGestionnairesDisponibles() { return gestionnairesDisponibles; }
+ public void setGestionnairesDisponibles(List gestionnairesDisponibles) { this.gestionnairesDisponibles = gestionnairesDisponibles; }
+
+ public Membre getMembreDemandeur() { return membreDemandeur; }
+ public void setMembreDemandeur(Membre membreDemandeur) { this.membreDemandeur = membreDemandeur; }
+
+ public NouvelleDemande getNouvelleDemande() { return nouvelleDemande; }
+ public void setNouvelleDemande(NouvelleDemande nouvelleDemande) { this.nouvelleDemande = nouvelleDemande; }
+
+ public String getSearchFilter() { return searchFilter; }
+ public void setSearchFilter(String searchFilter) { this.searchFilter = searchFilter; }
+
+ public String getStatutFilter() { return statutFilter; }
+ public void setStatutFilter(String statutFilter) { this.statutFilter = statutFilter; }
+
+ public String getTypeFilter() { return typeFilter; }
+ public void setTypeFilter(String typeFilter) { this.typeFilter = typeFilter; }
+
+ public String getPrioriteFilter() { return prioriteFilter; }
+ public void setPrioriteFilter(String prioriteFilter) { this.prioriteFilter = prioriteFilter; }
+
+ public LocalDate getDateFilter() { return dateFilter; }
+ public void setDateFilter(LocalDate dateFilter) { this.dateFilter = dateFilter; }
+
+ public Long getGestionnaireAssignation() { return gestionnaireAssignation; }
+ public void setGestionnaireAssignation(Long gestionnaireAssignation) { this.gestionnaireAssignation = gestionnaireAssignation; }
+
+ public String getCommentaireAssignation() { return commentaireAssignation; }
+ public void setCommentaireAssignation(String commentaireAssignation) { this.commentaireAssignation = commentaireAssignation; }
+
+ public int getEnAttente() { return enAttente; }
+ public void setEnAttente(int enAttente) { this.enAttente = enAttente; }
+
+ public int getUrgentes() { return urgentes; }
+ public void setUrgentes(int urgentes) { this.urgentes = urgentes; }
+
+ public int getTraitees() { return traitees; }
+ public void setTraitees(int traitees) { this.traitees = traitees; }
+
+ public int getDelaiMoyenTraitement() { return delaiMoyenTraitement; }
+ public void setDelaiMoyenTraitement(int delaiMoyenTraitement) { this.delaiMoyenTraitement = delaiMoyenTraitement; }
+
+ public Demande getDemandeSelectionnee() { return demandeSelectionnee; }
+ public void setDemandeSelectionnee(Demande demandeSelectionnee) { this.demandeSelectionnee = demandeSelectionnee; }
+
+ // Classes internes
+ public static class Demande {
+ private Long id;
+ private String reference;
+ private String objet;
+ private String type;
+ private String statut;
+ private String priorite;
+ private String nomDemandeur;
+ private String numeroMembre;
+ private String telephoneDemandeur;
+ private LocalDate dateDepot;
+ private LocalDate dateEcheance;
+ private String heureDepot;
+ private String assigneA;
+ private String demandeur;
+ private boolean hasPiecesJointes = false;
+
+ // Getters et setters
+ public Long getId() { return id; }
+ public void setId(Long id) { this.id = id; }
+
+ public String getReference() { return reference; }
+ public void setReference(String reference) { this.reference = reference; }
+
+ public String getObjet() { return objet; }
+ public void setObjet(String objet) { this.objet = objet; }
+
+ public String getType() { return type; }
+ public void setType(String type) { this.type = type; }
+
+ public String getStatut() { return statut; }
+ public void setStatut(String statut) { this.statut = statut; }
+
+ public String getPriorite() { return priorite; }
+ public void setPriorite(String priorite) { this.priorite = priorite; }
+
+ public String getNomDemandeur() { return nomDemandeur; }
+ public void setNomDemandeur(String nomDemandeur) { this.nomDemandeur = nomDemandeur; }
+
+ public String getNumeroMembre() { return numeroMembre; }
+ public void setNumeroMembre(String numeroMembre) { this.numeroMembre = numeroMembre; }
+
+ public String getTelephoneDemandeur() { return telephoneDemandeur; }
+ public void setTelephoneDemandeur(String telephoneDemandeur) { this.telephoneDemandeur = telephoneDemandeur; }
+
+ public LocalDate getDateDepot() { return dateDepot; }
+ public void setDateDepot(LocalDate dateDepot) { this.dateDepot = dateDepot; }
+
+ public LocalDate getDateEcheance() { return dateEcheance; }
+ public void setDateEcheance(LocalDate dateEcheance) { this.dateEcheance = dateEcheance; }
+
+ public String getHeureDepot() { return heureDepot; }
+ public void setHeureDepot(String heureDepot) { this.heureDepot = heureDepot; }
+
+ public String getAssigneA() { return assigneA; }
+ public void setAssigneA(String assigneA) { this.assigneA = assigneA; }
+
+ public String getDemandeur() { return demandeur != null ? demandeur : nomDemandeur; }
+ public void setDemandeur(String demandeur) { this.demandeur = demandeur; }
+
+ public boolean isHasPiecesJointes() { return hasPiecesJointes; }
+ public void setHasPiecesJointes(boolean hasPiecesJointes) { this.hasPiecesJointes = hasPiecesJointes; }
+
+ // Propriétés dérivées
+ public String getNomCompletDemandeur() { return nomDemandeur; }
+ public String getInitialesDemandeur() {
+ if (nomDemandeur == null) return "??";
+ String[] parts = nomDemandeur.split(" ");
+ return parts.length >= 2 ? parts[0].substring(0,1) + parts[1].substring(0,1) : nomDemandeur.substring(0, Math.min(2, nomDemandeur.length()));
+ }
+
+ public String getTypeIcon() {
+ return switch (type) {
+ case "ADHESION" -> "pi-user-plus";
+ case "AIDE_FINANCIERE" -> "pi-money-bill";
+ case "CERTIFICAT" -> "pi-file";
+ case "MUTATION" -> "pi-arrow-right-arrow-left";
+ case "RECLAMATION" -> "pi-exclamation-triangle";
+ default -> "pi-question";
+ };
+ }
+
+ public String getTypeColorClass() {
+ return switch (type) {
+ case "ADHESION" -> "bg-blue-500";
+ case "AIDE_FINANCIERE" -> "bg-green-500";
+ case "CERTIFICAT" -> "bg-purple-500";
+ case "MUTATION" -> "bg-orange-500";
+ case "RECLAMATION" -> "bg-red-500";
+ default -> "bg-gray-500";
+ };
+ }
+
+ public String getStatutSeverity() {
+ return switch (statut) {
+ case "EN_ATTENTE" -> "warning";
+ case "EN_COURS" -> "info";
+ case "APPROUVEE" -> "success";
+ case "REJETEE" -> "danger";
+ case "URGENTE" -> "danger";
+ default -> "secondary";
+ };
+ }
+
+ public String getStatutIcon() {
+ return switch (statut) {
+ case "EN_ATTENTE" -> "pi-clock";
+ case "EN_COURS" -> "pi-spin pi-spinner";
+ case "APPROUVEE" -> "pi-check";
+ case "REJETEE" -> "pi-times";
+ case "URGENTE" -> "pi-exclamation-triangle";
+ default -> "pi-circle";
+ };
+ }
+
+ public String getPrioriteSeverity() {
+ return switch (priorite) {
+ case "URGENTE" -> "danger";
+ case "HAUTE" -> "warning";
+ case "NORMALE" -> "info";
+ case "BASSE" -> "secondary";
+ default -> "primary";
+ };
+ }
+
+ public String getPrioriteIcon() {
+ return switch (priorite) {
+ case "URGENTE" -> "pi-exclamation-triangle";
+ case "HAUTE" -> "pi-arrow-up";
+ case "NORMALE" -> "pi-minus";
+ case "BASSE" -> "pi-arrow-down";
+ default -> "pi-circle";
+ };
+ }
+
+ public String getDateDepotRelative() {
+ if (dateDepot == null) return "";
+ long jours = ChronoUnit.DAYS.between(dateDepot, LocalDate.now());
+ if (jours == 0) return "aujourd'hui";
+ if (jours == 1) return "hier";
+ return "il y a " + jours + " jours";
+ }
+
+ public String getEcheanceClass() {
+ if (dateEcheance == null) return "";
+ long jours = ChronoUnit.DAYS.between(LocalDate.now(), dateEcheance);
+ if (jours < 0) return "text-red-500 font-bold";
+ if (jours <= 3) return "text-orange-500 font-bold";
+ return "text-600";
+ }
+ }
+
+ public static class Membre {
+ private Long id;
+ private String nomComplet;
+ private String numeroMembre;
+
+ public Long getId() { return id; }
+ public void setId(Long id) { this.id = id; }
+
+ public String getNomComplet() { return nomComplet; }
+ public void setNomComplet(String nomComplet) { this.nomComplet = nomComplet; }
+
+ public String getNumeroMembre() { return numeroMembre; }
+ public void setNumeroMembre(String numeroMembre) { this.numeroMembre = numeroMembre; }
+
+ public String getInitiales() {
+ if (nomComplet == null) return "??";
+ String[] parts = nomComplet.split(" ");
+ return parts.length >= 2 ? parts[0].substring(0,1) + parts[1].substring(0,1) : nomComplet.substring(0, Math.min(2, nomComplet.length()));
+ }
+ }
+
+ public static class NouvelleDemande {
+ private String objet;
+ private String type;
+ private String priorite;
+ private String description;
+ private LocalDate dateEcheance;
+ private Long assigneA;
+
+ public String getObjet() { return objet; }
+ public void setObjet(String objet) { this.objet = objet; }
+
+ public String getType() { return type; }
+ public void setType(String type) { this.type = type; }
+
+ public String getPriorite() { return priorite; }
+ public void setPriorite(String priorite) { this.priorite = priorite; }
+
+ public String getDescription() { return description; }
+ public void setDescription(String description) { this.description = description; }
+
+ public LocalDate getDateEcheance() { return dateEcheance; }
+ public void setDateEcheance(LocalDate dateEcheance) { this.dateEcheance = dateEcheance; }
+
+ public Long getAssigneA() { return assigneA; }
+ public void setAssigneA(Long assigneA) { this.assigneA = assigneA; }
+ }
+
+ public static class Gestionnaire {
+ private Long id;
+ private String nom;
+
+ public Gestionnaire() {}
+
+ public Gestionnaire(Long id, String nom) {
+ this.id = id;
+ this.nom = nom;
+ }
+
+ public Long getId() { return id; }
+ public void setId(Long id) { this.id = id; }
+
+ public String getNom() { return nom; }
+ public void setNom(String nom) { this.nom = nom; }
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/DocumentsBean.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/DocumentsBean.java
new file mode 100644
index 0000000..2148b07
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/DocumentsBean.java
@@ -0,0 +1,690 @@
+package dev.lions.unionflow.client.view;
+
+import jakarta.enterprise.context.SessionScoped;
+import jakarta.inject.Named;
+import jakarta.annotation.PostConstruct;
+import java.io.Serializable;
+import java.time.LocalDate;
+import java.time.LocalDateTime;
+import java.time.format.DateTimeFormatter;
+import java.time.temporal.ChronoUnit;
+import java.util.ArrayList;
+import java.util.List;
+import java.util.stream.Collectors;
+
+@Named("documentsBean")
+@SessionScoped
+public class DocumentsBean implements Serializable {
+
+ private static final long serialVersionUID = 1L;
+
+ private List tousLesDocuments;
+ private List documentsFiltres;
+ private List documentsSelectionnes;
+ private List dossiersAffichage;
+ private List dossiersDisponibles;
+ private List cheminNavigation;
+
+ private Document documentSelectionne;
+ private Dossier dossierSelectionne;
+ private NouveauDocument nouveauDocument;
+ private Filtres filtres;
+ private StatistiquesDocuments statistiques;
+
+ private String modeAffichage = "GRID"; // GRID ou LIST
+ private Long dossierActuelId;
+
+ @PostConstruct
+ public void init() {
+ initializeFiltres();
+ initializeStatistiques();
+ initializeDossiers();
+ initializeDocuments();
+ initializeNouveauDocument();
+ initializeNavigation();
+ appliquerFiltres();
+ }
+
+ private void initializeFiltres() {
+ filtres = new Filtres();
+ documentsSelectionnes = new ArrayList<>();
+ }
+
+ private void initializeStatistiques() {
+ statistiques = new StatistiquesDocuments();
+ statistiques.setTotalDocuments(1847);
+ statistiques.setTotalDossiers(23);
+ statistiques.setEspaceUtilise("2.3 GB");
+ statistiques.setPartagesMois(156);
+ }
+
+ private void initializeDossiers() {
+ dossiersAffichage = new ArrayList<>();
+ dossiersDisponibles = new ArrayList<>();
+
+ String[] nomsDossiers = {
+ "Documents Administratifs", "Finances et Comptabilité", "Ressources Humaines",
+ "Communication", "Formations", "Projets et Actions", "Archives 2023",
+ "Modèles et Templates", "Rapports Mensuels", "Juridique et Conformité"
+ };
+
+ String[] couleurs = {
+ "blue-500", "green-500", "orange-500", "purple-500", "indigo-500",
+ "teal-500", "gray-500", "pink-500", "yellow-500", "red-500"
+ };
+
+ for (int i = 0; i < nomsDossiers.length; i++) {
+ Dossier dossier = new Dossier();
+ dossier.setId((long) (i + 1));
+ dossier.setNom(nomsDossiers[i]);
+ dossier.setCouleur(couleurs[i % couleurs.length]);
+ dossier.setNombreDocuments(15 + (i * 8));
+ dossier.setDerniereModification(LocalDateTime.now().minusDays(i + 1));
+ dossier.setCheminComplet("/" + nomsDossiers[i]);
+
+ dossiersAffichage.add(dossier);
+ dossiersDisponibles.add(dossier);
+ }
+ }
+
+ private void initializeDocuments() {
+ tousLesDocuments = new ArrayList<>();
+
+ String[] noms = {
+ "Règlement Intérieur 2024.pdf", "Budget Prévisionnel Q1.xlsx", "Procès-Verbal AG Mars.docx",
+ "Guide Nouveau Membre.pdf", "Rapport Activités Janvier.docx", "Factures Fournisseurs Q4.xlsx",
+ "Statuts Association.pdf", "Plan Communication 2024.pptx", "Formation Leadership.pdf",
+ "Rapport Financier Annuel.pdf", "Convention Partenariat.docx", "Charte Graphique.pdf",
+ "Manuel Procédures.docx", "Bilan Social 2023.xlsx", "Certificat Conformité.pdf",
+ "Guide Utilisateur Plateforme.pdf", "Contrat Assurance.pdf", "Rapport Audit.docx",
+ "Plan Stratégique 3 ans.pptx", "Inventaire Matériel.xlsx", "Politique RGPD.pdf"
+ };
+
+ String[] types = {"PDF", "EXCEL", "WORD", "PDF", "WORD", "EXCEL", "PDF", "POWERPOINT", "PDF", "PDF", "WORD", "PDF", "WORD", "EXCEL", "PDF", "PDF", "PDF", "WORD", "POWERPOINT", "EXCEL", "PDF"};
+ String[] categories = {"ADMINISTRATIF", "FINANCIER", "ADMINISTRATIF", "FORMATION", "ADMINISTRATIF", "FINANCIER", "JURIDIQUE", "COMMUNICATION", "FORMATION", "FINANCIER", "JURIDIQUE", "COMMUNICATION", "ADMINISTRATIF", "FINANCIER", "JURIDIQUE", "FORMATION", "JURIDIQUE", "FINANCIER", "ADMINISTRATIF", "ADMINISTRATIF", "JURIDIQUE"};
+ String[] statuts = {"VALIDE", "VALIDE", "BROUILLON", "VALIDE", "VALIDE", "ARCHIVE", "VALIDE", "BROUILLON", "VALIDE", "VALIDE", "VALIDE", "VALIDE", "BROUILLON", "ARCHIVE", "VALIDE", "VALIDE", "VALIDE", "VALIDE", "BROUILLON", "VALIDE", "VALIDE"};
+ String[] auteurs = {"Marie Kouassi", "Paul Traoré", "Fatou Sanogo", "Jean Ouattara", "Aissata Koné", "Ibrahim Touré", "Aminata Bakayoko", "Yves Koffi", "Mariam Coulibaly", "Seydou Cissé", "Adjoa Mensah"};
+
+ long[] tailles = {2047000, 845000, 1250000, 3100000, 890000, 1450000, 567000, 2800000, 1900000, 3400000, 780000, 1200000, 1850000, 920000, 450000, 2200000, 890000, 1650000, 4200000, 680000, 750000};
+
+ for (int i = 0; i < noms.length; i++) {
+ Document document = new Document();
+ document.setId((long) (i + 1));
+ document.setNom(noms[i]);
+ document.setType(types[i]);
+ document.setCategorie(categories[i]);
+ document.setStatut(statuts[i]);
+ document.setAuteur(auteurs[i % auteurs.length]);
+ document.setTailleBytes(tailles[i]);
+ document.setDateCreation(LocalDateTime.now().minusDays(i * 3 + 1));
+ document.setDateModification(LocalDateTime.now().minusDays(i + 1));
+ document.setNombreVues(25 + (i * 7));
+ document.setNombreTelecharements(5 + (i * 2));
+
+ // Description automatique
+ document.setDescription("Document " + categories[i].toLowerCase() + " - " + noms[i]);
+
+ // Mots-clés automatiques
+ document.setMotsCles(generateMotsCles(categories[i], types[i]));
+
+ // Dossier parent (certains documents sont à la racine)
+ if (i % 3 != 0) {
+ document.setDossierId((long) ((i % dossiersDisponibles.size()) + 1));
+ }
+
+ tousLesDocuments.add(document);
+ }
+ }
+
+ private String generateMotsCles(String categorie, String type) {
+ String base = categorie.toLowerCase().replace("_", " ");
+ String typeClean = type.toLowerCase();
+ return base + ", " + typeClean + ", officiel, important";
+ }
+
+ private void initializeNouveauDocument() {
+ nouveauDocument = new NouveauDocument();
+ nouveauDocument.setAccesRestreint(false);
+ }
+
+ private void initializeNavigation() {
+ cheminNavigation = new ArrayList<>();
+
+ NiveauNavigation racine = new NiveauNavigation();
+ racine.setNom("📁 Racine");
+ racine.setDossierId(null);
+ cheminNavigation.add(racine);
+
+ // Si on est dans un dossier spécifique, ajouter le niveau
+ if (dossierActuelId != null) {
+ Dossier dossierActuel = dossiersDisponibles.stream()
+ .filter(d -> d.getId().equals(dossierActuelId))
+ .findFirst()
+ .orElse(null);
+
+ if (dossierActuel != null) {
+ NiveauNavigation niveau = new NiveauNavigation();
+ niveau.setNom(dossierActuel.getNom());
+ niveau.setDossierId(dossierActuel.getId());
+ cheminNavigation.add(niveau);
+ }
+ }
+ }
+
+ private void appliquerFiltres() {
+ documentsFiltres = tousLesDocuments.stream()
+ .filter(this::appliquerFiltre)
+ .collect(Collectors.toList());
+ }
+
+ private boolean appliquerFiltre(Document document) {
+ // Filtre par dossier actuel
+ if (dossierActuelId != null) {
+ if (document.getDossierId() == null || !document.getDossierId().equals(dossierActuelId)) {
+ return false;
+ }
+ } else {
+ // Si on est à la racine, ne montrer que les documents sans dossier parent
+ if (document.getDossierId() != null) {
+ return false;
+ }
+ }
+
+ if (filtres.getNom() != null && !filtres.getNom().trim().isEmpty()) {
+ if (!document.getNom().toLowerCase().contains(filtres.getNom().toLowerCase())) {
+ return false;
+ }
+ }
+
+ if (filtres.getType() != null && !filtres.getType().trim().isEmpty()) {
+ if (!document.getType().equals(filtres.getType())) {
+ return false;
+ }
+ }
+
+ if (filtres.getCategorie() != null && !filtres.getCategorie().trim().isEmpty()) {
+ if (!document.getCategorie().equals(filtres.getCategorie())) {
+ return false;
+ }
+ }
+
+ if (filtres.getStatut() != null && !filtres.getStatut().trim().isEmpty()) {
+ if (!document.getStatut().equals(filtres.getStatut())) {
+ return false;
+ }
+ }
+
+ if (filtres.getAuteur() != null && !filtres.getAuteur().trim().isEmpty()) {
+ if (!document.getAuteur().toLowerCase().contains(filtres.getAuteur().toLowerCase())) {
+ return false;
+ }
+ }
+
+ if (filtres.getMotsCles() != null && !filtres.getMotsCles().trim().isEmpty()) {
+ if (!document.getMotsCles().toLowerCase().contains(filtres.getMotsCles().toLowerCase())) {
+ return false;
+ }
+ }
+
+ if (filtres.getDateDebut() != null) {
+ if (document.getDateCreation().toLocalDate().isBefore(filtres.getDateDebut())) {
+ return false;
+ }
+ }
+
+ if (filtres.getDateFin() != null) {
+ if (document.getDateCreation().toLocalDate().isAfter(filtres.getDateFin())) {
+ return false;
+ }
+ }
+
+ if (filtres.getTailleMax() != null && filtres.getTailleMax() > 0) {
+ long tailleMaxBytes = filtres.getTailleMax().longValue() * 1024 * 1024; // Conversion MB vers bytes
+ if (document.getTailleBytes() > tailleMaxBytes) {
+ return false;
+ }
+ }
+
+ return true;
+ }
+
+ // Actions
+ public void rechercher() {
+ appliquerFiltres();
+ }
+
+ public void reinitialiserFiltres() {
+ filtres = new Filtres();
+ appliquerFiltres();
+ }
+
+ public void changerModeAffichage(String mode) {
+ this.modeAffichage = mode;
+ }
+
+ public void naviguerVersDossier(Dossier dossier) {
+ this.dossierActuelId = dossier.getId();
+ initializeNavigation();
+ appliquerFiltres();
+ }
+
+ public void telechargerNouveauDocument() {
+ Document nouveau = new Document();
+ nouveau.setId((long) (tousLesDocuments.size() + 1));
+ nouveau.setNom("Nouveau Document " + (tousLesDocuments.size() + 1));
+ nouveau.setCategorie(nouveauDocument.getCategorie());
+ nouveau.setDescription(nouveauDocument.getDescription());
+ nouveau.setMotsCles(nouveauDocument.getMotsCles());
+ nouveau.setDossierId(nouveauDocument.getDossierId());
+ nouveau.setStatut("BROUILLON");
+ nouveau.setAuteur("Utilisateur Actuel");
+ nouveau.setDateCreation(LocalDateTime.now());
+ nouveau.setDateModification(LocalDateTime.now());
+ nouveau.setTailleBytes(1024000L); // 1MB par défaut
+ nouveau.setNombreVues(0);
+ nouveau.setNombreTelecharements(0);
+ nouveau.setType("PDF"); // Type par défaut
+
+ tousLesDocuments.add(nouveau);
+ appliquerFiltres();
+
+ System.out.println("Document téléchargé: " + nouveau.getNom());
+ initializeNouveauDocument();
+ }
+
+ public void telechargerDocument(Document document) {
+ document.setNombreTelecharements(document.getNombreTelecharements() + 1);
+ System.out.println("Téléchargement du document: " + document.getNom());
+ }
+
+ public void supprimerDocument(Document document) {
+ tousLesDocuments.remove(document);
+ appliquerFiltres();
+ System.out.println("Document supprimé: " + document.getNom());
+ }
+
+ public void dupliquerDocument() {
+ if (documentSelectionne != null) {
+ Document copie = new Document();
+ copie.setId((long) (tousLesDocuments.size() + 1));
+ copie.setNom(documentSelectionne.getNom() + " (Copie)");
+ copie.setType(documentSelectionne.getType());
+ copie.setCategorie(documentSelectionne.getCategorie());
+ copie.setStatut("BROUILLON");
+ copie.setAuteur("Utilisateur Actuel");
+ copie.setDescription(documentSelectionne.getDescription());
+ copie.setMotsCles(documentSelectionne.getMotsCles());
+ copie.setDossierId(documentSelectionne.getDossierId());
+ copie.setTailleBytes(documentSelectionne.getTailleBytes());
+ copie.setDateCreation(LocalDateTime.now());
+ copie.setDateModification(LocalDateTime.now());
+ copie.setNombreVues(0);
+ copie.setNombreTelecharements(0);
+
+ tousLesDocuments.add(copie);
+ appliquerFiltres();
+ System.out.println("Document dupliqué: " + copie.getNom());
+ }
+ }
+
+ public void archiverDocument() {
+ if (documentSelectionne != null) {
+ documentSelectionne.setStatut("ARCHIVE");
+ System.out.println("Document archivé: " + documentSelectionne.getNom());
+ appliquerFiltres();
+ }
+ }
+
+ public void supprimerDefinitivement() {
+ if (documentSelectionne != null) {
+ tousLesDocuments.remove(documentSelectionne);
+ appliquerFiltres();
+ System.out.println("Document supprimé définitivement: " + documentSelectionne.getNom());
+ }
+ }
+
+ public String voirHistoriqueVersions() {
+ return "/pages/admin/documents/versions?id=" + documentSelectionne.getId() + "&faces-redirect=true";
+ }
+
+ public boolean estSelectionne(Document document) {
+ return documentsSelectionnes.contains(document);
+ }
+
+ public void toggleSelection(Document document) {
+ if (documentsSelectionnes.contains(document)) {
+ documentsSelectionnes.remove(document);
+ } else {
+ documentsSelectionnes.add(document);
+ }
+ }
+
+ // Getters et Setters
+ public List getTousLesDocuments() { return tousLesDocuments; }
+ public void setTousLesDocuments(List tousLesDocuments) { this.tousLesDocuments = tousLesDocuments; }
+
+ public List getDocumentsFiltres() { return documentsFiltres; }
+ public void setDocumentsFiltres(List documentsFiltres) { this.documentsFiltres = documentsFiltres; }
+
+ public List getDocumentsSelectionnes() { return documentsSelectionnes; }
+ public void setDocumentsSelectionnes(List documentsSelectionnes) { this.documentsSelectionnes = documentsSelectionnes; }
+
+ public List getDossiersAffichage() { return dossiersAffichage; }
+ public void setDossiersAffichage(List dossiersAffichage) { this.dossiersAffichage = dossiersAffichage; }
+
+ public List getDossiersDisponibles() { return dossiersDisponibles; }
+ public void setDossiersDisponibles(List dossiersDisponibles) { this.dossiersDisponibles = dossiersDisponibles; }
+
+ public List getCheminNavigation() { return cheminNavigation; }
+ public void setCheminNavigation(List cheminNavigation) { this.cheminNavigation = cheminNavigation; }
+
+ public Document getDocumentSelectionne() { return documentSelectionne; }
+ public void setDocumentSelectionne(Document documentSelectionne) { this.documentSelectionne = documentSelectionne; }
+
+ public Dossier getDossierSelectionne() { return dossierSelectionne; }
+ public void setDossierSelectionne(Dossier dossierSelectionne) { this.dossierSelectionne = dossierSelectionne; }
+
+ public NouveauDocument getNouveauDocument() { return nouveauDocument; }
+ public void setNouveauDocument(NouveauDocument nouveauDocument) { this.nouveauDocument = nouveauDocument; }
+
+ public Filtres getFiltres() { return filtres; }
+ public void setFiltres(Filtres filtres) { this.filtres = filtres; }
+
+ public StatistiquesDocuments getStatistiques() { return statistiques; }
+ public void setStatistiques(StatistiquesDocuments statistiques) { this.statistiques = statistiques; }
+
+ public String getModeAffichage() { return modeAffichage; }
+ public void setModeAffichage(String modeAffichage) { this.modeAffichage = modeAffichage; }
+
+ public Long getDossierActuelId() { return dossierActuelId; }
+ public void setDossierActuelId(Long dossierActuelId) { this.dossierActuelId = dossierActuelId; }
+
+ // Classes internes
+ public static class Document {
+ private Long id;
+ private String nom;
+ private String description;
+ private String type;
+ private String categorie;
+ private String statut;
+ private String auteur;
+ private String motsCles;
+ private Long dossierId;
+ private long tailleBytes;
+ private LocalDateTime dateCreation;
+ private LocalDateTime dateModification;
+ private int nombreVues;
+ private int nombreTelecharements;
+ private boolean accesRestreint;
+
+ // Getters et setters
+ public Long getId() { return id; }
+ public void setId(Long id) { this.id = id; }
+
+ public String getNom() { return nom; }
+ public void setNom(String nom) { this.nom = nom; }
+
+ public String getDescription() { return description; }
+ public void setDescription(String description) { this.description = description; }
+
+ public String getType() { return type; }
+ public void setType(String type) { this.type = type; }
+
+ public String getCategorie() { return categorie; }
+ public void setCategorie(String categorie) { this.categorie = categorie; }
+
+ public String getStatut() { return statut; }
+ public void setStatut(String statut) { this.statut = statut; }
+
+ public String getAuteur() { return auteur; }
+ public void setAuteur(String auteur) { this.auteur = auteur; }
+
+ public String getMotsCles() { return motsCles; }
+ public void setMotsCles(String motsCles) { this.motsCles = motsCles; }
+
+ public Long getDossierId() { return dossierId; }
+ public void setDossierId(Long dossierId) { this.dossierId = dossierId; }
+
+ public long getTailleBytes() { return tailleBytes; }
+ public void setTailleBytes(long tailleBytes) { this.tailleBytes = tailleBytes; }
+
+ public LocalDateTime getDateCreation() { return dateCreation; }
+ public void setDateCreation(LocalDateTime dateCreation) { this.dateCreation = dateCreation; }
+
+ public LocalDateTime getDateModification() { return dateModification; }
+ public void setDateModification(LocalDateTime dateModification) { this.dateModification = dateModification; }
+
+ public int getNombreVues() { return nombreVues; }
+ public void setNombreVues(int nombreVues) { this.nombreVues = nombreVues; }
+
+ public int getNombreTelecharements() { return nombreTelecharements; }
+ public void setNombreTelecharements(int nombreTelecharements) { this.nombreTelecharements = nombreTelecharements; }
+
+ public boolean isAccesRestreint() { return accesRestreint; }
+ public void setAccesRestreint(boolean accesRestreint) { this.accesRestreint = accesRestreint; }
+
+ // Propriétés dérivées
+ public String getTypeIcon() {
+ return switch (type) {
+ case "PDF" -> "pi-file-pdf";
+ case "WORD" -> "pi-file-word";
+ case "EXCEL" -> "pi-file-excel";
+ case "POWERPOINT" -> "pi-file";
+ case "IMAGE" -> "pi-image";
+ default -> "pi-file";
+ };
+ }
+
+ public String getTypeCouleur() {
+ return switch (type) {
+ case "PDF" -> "red-500";
+ case "WORD" -> "blue-500";
+ case "EXCEL" -> "green-500";
+ case "POWERPOINT" -> "orange-500";
+ case "IMAGE" -> "purple-500";
+ default -> "gray-500";
+ };
+ }
+
+ public String getCategorieLibelle() {
+ return switch (categorie) {
+ case "ADMINISTRATIF" -> "Administratif";
+ case "FINANCIER" -> "Financier";
+ case "JURIDIQUE" -> "Juridique";
+ case "COMMUNICATION" -> "Communication";
+ case "FORMATION" -> "Formation";
+ case "AUTRE" -> "Autre";
+ default -> categorie;
+ };
+ }
+
+ public String getCategorieSeverity() {
+ return switch (categorie) {
+ case "ADMINISTRATIF" -> "info";
+ case "FINANCIER" -> "success";
+ case "JURIDIQUE" -> "danger";
+ case "COMMUNICATION" -> "warning";
+ case "FORMATION" -> "primary";
+ case "AUTRE" -> "secondary";
+ default -> "secondary";
+ };
+ }
+
+ public String getStatutLibelle() {
+ return switch (statut) {
+ case "BROUILLON" -> "Brouillon";
+ case "VALIDE" -> "Validé";
+ case "ARCHIVE" -> "Archivé";
+ case "EXPIRE" -> "Expiré";
+ default -> statut;
+ };
+ }
+
+ public String getStatutSeverity() {
+ return switch (statut) {
+ case "BROUILLON" -> "warning";
+ case "VALIDE" -> "success";
+ case "ARCHIVE" -> "secondary";
+ case "EXPIRE" -> "danger";
+ default -> "secondary";
+ };
+ }
+
+ public String getTaille() {
+ if (tailleBytes < 1024) {
+ return tailleBytes + " B";
+ } else if (tailleBytes < 1024 * 1024) {
+ return Math.round(tailleBytes / 1024.0) + " KB";
+ } else {
+ return Math.round(tailleBytes / (1024.0 * 1024)) + " MB";
+ }
+ }
+
+ public String getDateCreationFormatee() {
+ if (dateCreation == null) return "";
+ return dateCreation.format(DateTimeFormatter.ofPattern("dd/MM/yyyy"));
+ }
+
+ public String getDateCreationRelative() {
+ if (dateCreation == null) return "";
+ long jours = ChronoUnit.DAYS.between(dateCreation.toLocalDate(), LocalDate.now());
+ if (jours == 0) return "Aujourd'hui";
+ if (jours == 1) return "Hier";
+ if (jours < 7) return "Il y a " + jours + " jours";
+ if (jours < 30) return "Il y a " + (jours / 7) + " semaine" + (jours / 7 > 1 ? "s" : "");
+ return "Il y a " + (jours / 30) + " mois";
+ }
+ }
+
+ public static class Dossier {
+ private Long id;
+ private String nom;
+ private String couleur;
+ private int nombreDocuments;
+ private LocalDateTime derniereModification;
+ private String cheminComplet;
+
+ // Getters et setters
+ public Long getId() { return id; }
+ public void setId(Long id) { this.id = id; }
+
+ public String getNom() { return nom; }
+ public void setNom(String nom) { this.nom = nom; }
+
+ public String getCouleur() { return couleur; }
+ public void setCouleur(String couleur) { this.couleur = couleur; }
+
+ public int getNombreDocuments() { return nombreDocuments; }
+ public void setNombreDocuments(int nombreDocuments) { this.nombreDocuments = nombreDocuments; }
+
+ public LocalDateTime getDerniereModification() { return derniereModification; }
+ public void setDerniereModification(LocalDateTime derniereModification) { this.derniereModification = derniereModification; }
+
+ public String getCheminComplet() { return cheminComplet; }
+ public void setCheminComplet(String cheminComplet) { this.cheminComplet = cheminComplet; }
+
+ public String getDerniereModificationRelative() {
+ if (derniereModification == null) return "";
+ long jours = ChronoUnit.DAYS.between(derniereModification.toLocalDate(), LocalDate.now());
+ if (jours == 0) return "aujourd'hui";
+ if (jours == 1) return "hier";
+ return "il y a " + jours + " jours";
+ }
+ }
+
+ public static class NouveauDocument {
+ private String categorie;
+ private String description;
+ private String motsCles;
+ private Long dossierId;
+ private boolean accesRestreint;
+
+ // Getters et setters
+ public String getCategorie() { return categorie; }
+ public void setCategorie(String categorie) { this.categorie = categorie; }
+
+ public String getDescription() { return description; }
+ public void setDescription(String description) { this.description = description; }
+
+ public String getMotsCles() { return motsCles; }
+ public void setMotsCles(String motsCles) { this.motsCles = motsCles; }
+
+ public Long getDossierId() { return dossierId; }
+ public void setDossierId(Long dossierId) { this.dossierId = dossierId; }
+
+ public boolean isAccesRestreint() { return accesRestreint; }
+ public void setAccesRestreint(boolean accesRestreint) { this.accesRestreint = accesRestreint; }
+ }
+
+ public static class Filtres {
+ private String nom;
+ private String type;
+ private String categorie;
+ private String statut;
+ private String auteur;
+ private String motsCles;
+ private LocalDate dateDebut;
+ private LocalDate dateFin;
+ private Double tailleMax;
+
+ // Getters et setters
+ public String getNom() { return nom; }
+ public void setNom(String nom) { this.nom = nom; }
+
+ public String getType() { return type; }
+ public void setType(String type) { this.type = type; }
+
+ public String getCategorie() { return categorie; }
+ public void setCategorie(String categorie) { this.categorie = categorie; }
+
+ public String getStatut() { return statut; }
+ public void setStatut(String statut) { this.statut = statut; }
+
+ public String getAuteur() { return auteur; }
+ public void setAuteur(String auteur) { this.auteur = auteur; }
+
+ public String getMotsCles() { return motsCles; }
+ public void setMotsCles(String motsCles) { this.motsCles = motsCles; }
+
+ public LocalDate getDateDebut() { return dateDebut; }
+ public void setDateDebut(LocalDate dateDebut) { this.dateDebut = dateDebut; }
+
+ public LocalDate getDateFin() { return dateFin; }
+ public void setDateFin(LocalDate dateFin) { this.dateFin = dateFin; }
+
+ public Double getTailleMax() { return tailleMax; }
+ public void setTailleMax(Double tailleMax) { this.tailleMax = tailleMax; }
+ }
+
+ public static class StatistiquesDocuments {
+ private int totalDocuments;
+ private int totalDossiers;
+ private String espaceUtilise;
+ private int partagesMois;
+
+ // Getters et setters
+ public int getTotalDocuments() { return totalDocuments; }
+ public void setTotalDocuments(int totalDocuments) { this.totalDocuments = totalDocuments; }
+
+ public int getTotalDossiers() { return totalDossiers; }
+ public void setTotalDossiers(int totalDossiers) { this.totalDossiers = totalDossiers; }
+
+ public String getEspaceUtilise() { return espaceUtilise; }
+ public void setEspaceUtilise(String espaceUtilise) { this.espaceUtilise = espaceUtilise; }
+
+ public int getPartagesMois() { return partagesMois; }
+ public void setPartagesMois(int partagesMois) { this.partagesMois = partagesMois; }
+ }
+
+ public static class NiveauNavigation {
+ private String nom;
+ private Long dossierId;
+
+ // Getters et setters
+ public String getNom() { return nom; }
+ public void setNom(String nom) { this.nom = nom; }
+
+ public Long getDossierId() { return dossierId; }
+ public void setDossierId(Long dossierId) { this.dossierId = dossierId; }
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/EntitesGestionBean.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/EntitesGestionBean.java
new file mode 100644
index 0000000..1a3b302
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/EntitesGestionBean.java
@@ -0,0 +1,706 @@
+package dev.lions.unionflow.client.view;
+
+import jakarta.enterprise.context.SessionScoped;
+import jakarta.inject.Named;
+import jakarta.annotation.PostConstruct;
+import java.io.Serializable;
+import java.time.LocalDate;
+import java.time.LocalDateTime;
+import java.time.format.DateTimeFormatter;
+import java.time.temporal.ChronoUnit;
+import java.util.ArrayList;
+import java.util.List;
+import java.util.stream.Collectors;
+
+@Named("entitesGestionBean")
+@SessionScoped
+public class EntitesGestionBean implements Serializable {
+
+ private static final long serialVersionUID = 1L;
+
+ private List toutesLesEntites;
+ private List entitesFiltrees;
+ private List entitesSelectionnees;
+ private Entite entiteSelectionne;
+ private Entite nouvelleEntite;
+ private Filtres filtres;
+ private Statistiques statistiques;
+
+ @PostConstruct
+ public void init() {
+ initializeFiltres();
+ initializeEntites();
+ initializeStatistiques();
+ initializeNouvelleEntite();
+ appliquerFiltres();
+ }
+
+ private void initializeFiltres() {
+ filtres = new Filtres();
+ entitesSelectionnees = new ArrayList<>();
+ }
+
+ private void initializeStatistiques() {
+ statistiques = new Statistiques();
+ statistiques.setTotalEntites(127); // Nouvelle stratégie volume
+ statistiques.setEntitesActives(127);
+ statistiques.setTotalMembres(18547); // 146 membres/organisation en moyenne
+ statistiques.setMoyenneMembresParEntite(146); // Moyenne calculée
+ statistiques.setRevenus("363 000 FCFA");
+ statistiques.setSouscriptionsExpirantes(12);
+ statistiques.setEntitesQuotaAtteint(8);
+ statistiques.setFormulairePopulaire("Standard");
+ statistiques.setTauxRenouvellement(94.2f);
+
+ // Calcul dynamique des statistiques de souscription
+ calculerStatistiquesSouscriptions();
+ }
+
+ private void initializeEntites() {
+ toutesLesEntites = new ArrayList<>();
+
+ // Génération de données de test
+ String[] noms = {
+ "Association Alpha Centrale", "Club Beta Régional", "Groupe Gamma Local",
+ "Association Delta Nord", "Club Epsilon Sud", "Groupe Zeta Jeunes",
+ "Association Eta Ouest", "Club Theta Est", "Groupe Iota Centre",
+ "Association Kappa Métropole", "Branche Féminine Lambda", "Club Mu Urbain",
+ "Groupe Jeunes Nu", "Association Xi Rural", "Club Omicron Mixte"
+ };
+
+ String[] types = {
+ "ASSOCIATION", "CLUB", "GROUPE", "ASSOCIATION", "CLUB", "GROUPE_JEUNES",
+ "ASSOCIATION", "CLUB", "GROUPE", "ASSOCIATION", "BRANCHE", "CLUB",
+ "GROUPE_JEUNES", "ASSOCIATION", "CLUB"
+ };
+
+ String[] regions = {
+ "REGION_1", "REGION_2", "REGION_3", "REGION_4", "REGION_5", "REGION_1",
+ "REGION_6", "REGION_7", "REGION_8", "REGION_9", "REGION_1", "REGION_10",
+ "REGION_2", "REGION_11", "REGION_12"
+ };
+
+ String[] statuts = {
+ "ACTIVE", "ACTIVE", "ACTIVE", "ACTIVE", "ACTIVE", "ACTIVE",
+ "ACTIVE", "SUSPENDUE", "ACTIVE", "ACTIVE", "ACTIVE", "INACTIVE",
+ "ACTIVE", "ACTIVE", "ACTIVE"
+ };
+
+ int[] nombresMembres = {156, 123, 98, 87, 73, 45, 67, 0, 54, 43, 32, 0, 28, 38, 51};
+
+ for (int i = 0; i < noms.length; i++) {
+ Entite entite = new Entite();
+ entite.setId((long) (i + 1));
+ entite.setNom(noms[i]);
+ entite.setCodeEntite("ENT" + String.format("%03d", i + 1));
+ entite.setType(types[i]);
+ entite.setRegion(regions[i]);
+ entite.setStatut(statuts[i]);
+ entite.setNombreMembres(nombresMembres[i]);
+ entite.setMembresUtilises(nombresMembres[i]);
+ entite.setAdresse("Adresse " + noms[i]);
+ entite.setTelephone("77 123 45 " + String.format("%02d", i + 1));
+ entite.setEmail(noms[i].toLowerCase().replace(" ", ".") + "@unionflow.app");
+ entite.setDescription("Description de " + noms[i]);
+ entite.setDerniereActivite(LocalDateTime.now().minusDays(i * 2 + 1));
+
+ // Définir le forfait selon le nombre de membres
+ if (nombresMembres[i] <= 100) {
+ entite.setForfaitSouscrit("Starter");
+ entite.setMembresQuota(100);
+ entite.setMontantMensuel("2 000 FCFA");
+ } else if (nombresMembres[i] <= 200) {
+ entite.setForfaitSouscrit("Standard");
+ entite.setMembresQuota(200);
+ entite.setMontantMensuel("3 000 FCFA");
+ } else if (nombresMembres[i] <= 500) {
+ entite.setForfaitSouscrit("Premium");
+ entite.setMembresQuota(500);
+ entite.setMontantMensuel("4 000 FCFA");
+ } else {
+ entite.setForfaitSouscrit("Cristal");
+ entite.setMembresQuota(2000);
+ entite.setMontantMensuel("5 000 FCFA");
+ }
+
+ // Date d'expiration (varie entre 1 mois et 11 mois)
+ entite.setDateExpirationSouscription(LocalDate.now().plusMonths(1 + (i % 11)));
+
+ // Administrateur
+ if (nombresMembres[i] > 0) {
+ Administrateur admin = new Administrateur();
+ admin.setNomComplet("Admin " + (i + 1));
+ admin.setEmail("admin" + (i + 1) + "@unionflow.app");
+ entite.setAdministrateur(admin);
+ }
+
+ toutesLesEntites.add(entite);
+ }
+ }
+
+ private void initializeNouvelleEntite() {
+ nouvelleEntite = new Entite();
+ }
+
+ private void appliquerFiltres() {
+ entitesFiltrees = toutesLesEntites.stream()
+ .filter(this::appliquerFiltre)
+ .collect(Collectors.toList());
+ }
+
+ private boolean appliquerFiltre(Entite entite) {
+ // Filtre par nom
+ if (filtres.getNom() != null && !filtres.getNom().trim().isEmpty()) {
+ if (!entite.getNom().toLowerCase().contains(filtres.getNom().toLowerCase())) {
+ return false;
+ }
+ }
+
+ // Filtre par type
+ if (filtres.getType() != null && !filtres.getType().trim().isEmpty()) {
+ if (!entite.getType().equals(filtres.getType())) {
+ return false;
+ }
+ }
+
+ // Filtre par statut
+ if (filtres.getStatut() != null && !filtres.getStatut().trim().isEmpty()) {
+ if (!entite.getStatut().equals(filtres.getStatut())) {
+ return false;
+ }
+ }
+
+ // Filtre par région
+ if (filtres.getRegion() != null && !filtres.getRegion().trim().isEmpty()) {
+ if (!entite.getRegion().equals(filtres.getRegion())) {
+ return false;
+ }
+ }
+
+ // Filtre par forfait
+ if (filtres.getForfait() != null && !filtres.getForfait().trim().isEmpty()) {
+ if (!entite.getForfaitSouscrit().equals(filtres.getForfait())) {
+ return false;
+ }
+ }
+
+ // Filtre par alerte quota
+ if (filtres.getAlerteQuota() != null && !filtres.getAlerteQuota().trim().isEmpty()) {
+ if ("OUI".equals(filtres.getAlerteQuota()) && !entite.isQuotaProche()) {
+ return false;
+ }
+ if ("NON".equals(filtres.getAlerteQuota()) && entite.isQuotaProche()) {
+ return false;
+ }
+ }
+
+ // Filtre par alerte expiration
+ if (filtres.getAlerteExpiration() != null && !filtres.getAlerteExpiration().trim().isEmpty()) {
+ if ("OUI".equals(filtres.getAlerteExpiration()) && !entite.isExpirationProche()) {
+ return false;
+ }
+ if ("NON".equals(filtres.getAlerteExpiration()) && entite.isExpirationProche()) {
+ return false;
+ }
+ }
+
+ // Filtre par statut souscription
+ if (filtres.getStatutSouscription() != null && !filtres.getStatutSouscription().trim().isEmpty()) {
+ if (!entite.getStatutSouscription().equals(filtres.getStatutSouscription())) {
+ return false;
+ }
+ }
+
+ return true;
+ }
+
+ // Actions
+ public void rechercher() {
+ appliquerFiltres();
+ }
+
+ public void reinitialiserFiltres() {
+ filtres = new Filtres();
+ appliquerFiltres();
+ }
+
+ public String voirEntite(Entite entite) {
+ return "/pages/super-admin/entites/details?id=" + entite.getId() + "&faces-redirect=true";
+ }
+
+ public void creerEntite() {
+ nouvelleEntite.setId((long) (toutesLesEntites.size() + 1));
+ nouvelleEntite.setCodeEntite("ENT" + String.format("%03d", toutesLesEntites.size() + 1));
+ nouvelleEntite.setStatut("ACTIVE");
+ nouvelleEntite.setNombreMembres(0);
+ nouvelleEntite.setDerniereActivite(LocalDateTime.now());
+
+ toutesLesEntites.add(nouvelleEntite);
+ appliquerFiltres();
+
+ System.out.println("Nouvelle entité créée: " + nouvelleEntite.getNom());
+
+ initializeNouvelleEntite();
+ }
+
+ public String gererMembres() {
+ return "/pages/admin/membres/gestion?entiteId=" + entiteSelectionne.getId() + "&faces-redirect=true";
+ }
+
+ public String configurerEntite() {
+ return "/pages/super-admin/entites/configuration?id=" + entiteSelectionne.getId() + "&faces-redirect=true";
+ }
+
+ public String voirRapports() {
+ return "/pages/super-admin/entites/rapports?id=" + entiteSelectionne.getId() + "&faces-redirect=true";
+ }
+
+ public void suspendreEntite() {
+ entiteSelectionne.setStatut("SUSPENDUE");
+ System.out.println("Entité suspendue: " + entiteSelectionne.getNom());
+ appliquerFiltres();
+ }
+
+ public void reactiverEntite() {
+ entiteSelectionne.setStatut("ACTIVE");
+ System.out.println("Entité réactivée: " + entiteSelectionne.getNom());
+ appliquerFiltres();
+ }
+
+ public void supprimerEntite() {
+ toutesLesEntites.remove(entiteSelectionne);
+ System.out.println("Entité supprimée: " + entiteSelectionne.getNom());
+ appliquerFiltres();
+ }
+
+ public void exporterEntites() {
+ System.out.println("Export de " + entitesFiltrees.size() + " entités");
+ }
+
+ // Getters et Setters
+ public List getToutesLesEntites() { return toutesLesEntites; }
+ public void setToutesLesEntites(List toutesLesEntites) { this.toutesLesEntites = toutesLesEntites; }
+
+ public List getEntitesFiltrees() { return entitesFiltrees; }
+ public void setEntitesFiltrees(List entitesFiltrees) { this.entitesFiltrees = entitesFiltrees; }
+
+ public List getEntitesSelectionnees() { return entitesSelectionnees; }
+ public void setEntitesSelectionnees(List entitesSelectionnees) { this.entitesSelectionnees = entitesSelectionnees; }
+
+ public Entite getEntiteSelectionne() { return entiteSelectionne; }
+ public void setEntiteSelectionne(Entite entiteSelectionne) { this.entiteSelectionne = entiteSelectionne; }
+
+ public Entite getNouvelleEntite() { return nouvelleEntite; }
+ public void setNouvelleEntite(Entite nouvelleEntite) { this.nouvelleEntite = nouvelleEntite; }
+
+ public Filtres getFiltres() { return filtres; }
+ public void setFiltres(Filtres filtres) { this.filtres = filtres; }
+
+ public Statistiques getStatistiques() { return statistiques; }
+ public void setStatistiques(Statistiques statistiques) { this.statistiques = statistiques; }
+
+ // Méthodes utilitaires pour les souscriptions
+ private void calculerStatistiquesSouscriptions() {
+ if (toutesLesEntites == null || statistiques == null) {
+ return; // Sécurité si appelé avant initialisation complète
+ }
+
+ int expirantes = 0;
+ int quotaAtteint = 0;
+
+ for (Entite entite : toutesLesEntites) {
+ if (entite.isExpirationProche()) {
+ expirantes++;
+ }
+ if (entite.isQuotaAtteint()) {
+ quotaAtteint++;
+ }
+ }
+
+ statistiques.setSouscriptionsExpirantes(expirantes);
+ statistiques.setEntitesQuotaAtteint(quotaAtteint);
+ }
+
+ public void renouvelerSouscription() {
+ if (entiteSelectionne != null) {
+ entiteSelectionne.setDateExpirationSouscription(LocalDate.now().plusMonths(12));
+ entiteSelectionne.setStatutSouscription("ACTIVE");
+ System.out.println("Souscription renouvelée pour: " + entiteSelectionne.getNom());
+ appliquerFiltres();
+ }
+ }
+
+ public void upgraderForfait() {
+ if (entiteSelectionne != null) {
+ String forfaitActuel = entiteSelectionne.getForfaitSouscrit();
+ switch (forfaitActuel) {
+ case "Starter":
+ entiteSelectionne.setForfaitSouscrit("Standard");
+ entiteSelectionne.setMembresQuota(200);
+ entiteSelectionne.setMontantMensuel("3 000 FCFA");
+ break;
+ case "Standard":
+ entiteSelectionne.setForfaitSouscrit("Premium");
+ entiteSelectionne.setMembresQuota(500);
+ entiteSelectionne.setMontantMensuel("4 000 FCFA");
+ break;
+ case "Premium":
+ entiteSelectionne.setForfaitSouscrit("Cristal");
+ entiteSelectionne.setMembresQuota(2000);
+ entiteSelectionne.setMontantMensuel("5 000 FCFA");
+ break;
+ }
+ System.out.println("Forfait upgradé pour: " + entiteSelectionne.getNom());
+ appliquerFiltres();
+ }
+ }
+
+ public void gererQuotas() {
+ System.out.println("Gestion des quotas pour toutes les entités");
+ }
+
+ public void envoyerRelancesSouscriptions() {
+ int compteur = 0;
+ for (Entite entite : toutesLesEntites) {
+ if (entite.isExpirationProche()) {
+ System.out.println("Relance envoyée à: " + entite.getNom());
+ compteur++;
+ }
+ }
+ System.out.println(compteur + " relances de souscription envoyées");
+ }
+
+ // Actions groupées
+ public void renouvelerSouscriptionsGroupees() {
+ int compteur = 0;
+ for (Entite entite : entitesSelectionnees) {
+ entite.setDateExpirationSouscription(LocalDate.now().plusMonths(12));
+ entite.setStatutSouscription("ACTIVE");
+ compteur++;
+ }
+ System.out.println(compteur + " souscriptions renouvelées en masse");
+ entitesSelectionnees.clear();
+ appliquerFiltres();
+ }
+
+ public void suspendreEntitesGroupees() {
+ int compteur = 0;
+ for (Entite entite : entitesSelectionnees) {
+ entite.setStatut("SUSPENDUE");
+ compteur++;
+ }
+ System.out.println(compteur + " entités suspendues en masse");
+ entitesSelectionnees.clear();
+ appliquerFiltres();
+ }
+
+ public void reactiverEntitesGroupees() {
+ int compteur = 0;
+ for (Entite entite : entitesSelectionnees) {
+ entite.setStatut("ACTIVE");
+ compteur++;
+ }
+ System.out.println(compteur + " entités réactivées en masse");
+ entitesSelectionnees.clear();
+ appliquerFiltres();
+ }
+
+ public void proposerUpgradeGroupees() {
+ int compteur = 0;
+ for (Entite entite : entitesSelectionnees) {
+ if (entite.isQuotaProche()) {
+ // Simulation d'envoi de proposition d'upgrade
+ System.out.println("Proposition d'upgrade envoyée à: " + entite.getNom());
+ compteur++;
+ }
+ }
+ System.out.println(compteur + " propositions d'upgrade envoyées");
+ }
+
+ // Classes internes
+ public static class Entite {
+ private Long id;
+ private String nom;
+ private String codeEntite;
+ private String type;
+ private String region;
+ private String statut;
+ private int nombreMembres;
+ private String adresse;
+ private String telephone;
+ private String email;
+ private String description;
+ private LocalDateTime derniereActivite;
+ private Administrateur administrateur;
+
+ // Informations de souscription
+ private String forfaitSouscrit = "Standard";
+ private int membresQuota = 200;
+ private int membresUtilises;
+ private LocalDate dateExpirationSouscription;
+ private String statutSouscription = "ACTIVE";
+ private String montantMensuel = "3 000 FCFA";
+
+ // Getters et setters
+ public Long getId() { return id; }
+ public void setId(Long id) { this.id = id; }
+
+ public String getNom() { return nom; }
+ public void setNom(String nom) { this.nom = nom; }
+
+ public String getCodeEntite() { return codeEntite; }
+ public void setCodeEntite(String codeEntite) { this.codeEntite = codeEntite; }
+
+ public String getType() { return type; }
+ public void setType(String type) { this.type = type; }
+
+ public String getRegion() { return region; }
+ public void setRegion(String region) { this.region = region; }
+
+ public String getStatut() { return statut; }
+ public void setStatut(String statut) { this.statut = statut; }
+
+ public int getNombreMembres() { return nombreMembres; }
+ public void setNombreMembres(int nombreMembres) { this.nombreMembres = nombreMembres; }
+
+ public String getAdresse() { return adresse; }
+ public void setAdresse(String adresse) { this.adresse = adresse; }
+
+ public String getTelephone() { return telephone; }
+ public void setTelephone(String telephone) { this.telephone = telephone; }
+
+ public String getEmail() { return email; }
+ public void setEmail(String email) { this.email = email; }
+
+ public String getDescription() { return description; }
+ public void setDescription(String description) { this.description = description; }
+
+ public LocalDateTime getDerniereActivite() { return derniereActivite; }
+ public void setDerniereActivite(LocalDateTime derniereActivite) { this.derniereActivite = derniereActivite; }
+
+ public Administrateur getAdministrateur() { return administrateur; }
+ public void setAdministrateur(Administrateur administrateur) { this.administrateur = administrateur; }
+
+ // Propriétés dérivées
+ public String getTypeLibelle() {
+ return switch (type) {
+ case "ASSOCIATION" -> "Association";
+ case "CLUB" -> "Club";
+ case "GROUPE" -> "Groupe";
+ case "GROUPE_JEUNES" -> "Groupe Jeunes";
+ case "BRANCHE" -> "Branche";
+ default -> type;
+ };
+ }
+
+ public String getTypeSeverity() {
+ return switch (type) {
+ case "ASSOCIATION" -> "info";
+ case "CLUB" -> "success";
+ case "GROUPE" -> "warning";
+ case "GROUPE_JEUNES" -> "primary";
+ case "BRANCHE" -> "secondary";
+ default -> "secondary";
+ };
+ }
+
+ public String getTypeIcon() {
+ return switch (type) {
+ case "ASSOCIATION" -> "pi-users";
+ case "CLUB" -> "pi-home";
+ case "GROUPE" -> "pi-sitemap";
+ case "GROUPE_JEUNES" -> "pi-star";
+ case "BRANCHE" -> "pi-share-alt";
+ default -> "pi-building";
+ };
+ }
+
+ public String getStatutSeverity() {
+ return switch (statut) {
+ case "ACTIVE" -> "success";
+ case "INACTIVE" -> "warning";
+ case "SUSPENDUE" -> "danger";
+ default -> "secondary";
+ };
+ }
+
+ public String getStatutIcon() {
+ return switch (statut) {
+ case "ACTIVE" -> "pi-check";
+ case "INACTIVE" -> "pi-pause";
+ case "SUSPENDUE" -> "pi-ban";
+ default -> "pi-circle";
+ };
+ }
+
+ public String getDerniereActiviteFormatee() {
+ if (derniereActivite == null) return "N/A";
+ return derniereActivite.format(DateTimeFormatter.ofPattern("dd/MM/yyyy"));
+ }
+
+ public String getDerniereActiviteRelative() {
+ if (derniereActivite == null) return "";
+ long jours = ChronoUnit.DAYS.between(derniereActivite.toLocalDate(), LocalDate.now());
+ if (jours == 0) return "Aujourd'hui";
+ if (jours == 1) return "Hier";
+ if (jours < 7) return "Il y a " + jours + " jours";
+ if (jours < 30) return "Il y a " + (jours / 7) + " semaine" + (jours / 7 > 1 ? "s" : "");
+ return "Il y a " + (jours / 30) + " mois";
+ }
+
+ // Getters et setters pour les informations de souscription
+ public String getForfaitSouscrit() { return forfaitSouscrit; }
+ public void setForfaitSouscrit(String forfaitSouscrit) { this.forfaitSouscrit = forfaitSouscrit; }
+
+ public int getMembresQuota() { return membresQuota; }
+ public void setMembresQuota(int membresQuota) { this.membresQuota = membresQuota; }
+
+ public int getMembresUtilises() { return membresUtilises; }
+ public void setMembresUtilises(int membresUtilises) { this.membresUtilises = membresUtilises; }
+
+ public LocalDate getDateExpirationSouscription() { return dateExpirationSouscription; }
+ public void setDateExpirationSouscription(LocalDate dateExpirationSouscription) { this.dateExpirationSouscription = dateExpirationSouscription; }
+
+ public String getStatutSouscription() { return statutSouscription; }
+ public void setStatutSouscription(String statutSouscription) { this.statutSouscription = statutSouscription; }
+
+ public String getMontantMensuel() { return montantMensuel; }
+ public void setMontantMensuel(String montantMensuel) { this.montantMensuel = montantMensuel; }
+
+ // Méthodes utilitaires pour les souscriptions
+ public boolean isQuotaProche() {
+ return getMembresUtilises() >= (getMembresQuota() * 0.85);
+ }
+
+ public boolean isQuotaAtteint() {
+ return getMembresUtilises() >= getMembresQuota();
+ }
+
+ public boolean isExpirationProche() {
+ if (dateExpirationSouscription == null) return false;
+ return ChronoUnit.DAYS.between(LocalDate.now(), dateExpirationSouscription) <= 30;
+ }
+
+ public int getPourcentageUtilisationQuota() {
+ if (membresQuota == 0) return 0;
+ return (membresUtilises * 100) / membresQuota;
+ }
+
+ public String getForfaitCouleur() {
+ return switch (forfaitSouscrit) {
+ case "Starter" -> "primary";
+ case "Standard" -> "success";
+ case "Premium" -> "warning";
+ case "Cristal" -> "info";
+ default -> "secondary";
+ };
+ }
+
+ public String getForfaitIcone() {
+ return switch (forfaitSouscrit) {
+ case "Starter" -> "pi-star";
+ case "Standard" -> "pi-users";
+ case "Premium" -> "pi-crown";
+ case "Cristal" -> "pi-diamond";
+ default -> "pi-circle";
+ };
+ }
+
+ public long getJoursAvantExpiration() {
+ if (dateExpirationSouscription == null) return 0;
+ return ChronoUnit.DAYS.between(LocalDate.now(), dateExpirationSouscription);
+ }
+ }
+
+ public static class Administrateur {
+ private String nomComplet;
+ private String email;
+
+ // Getters et setters
+ public String getNomComplet() { return nomComplet; }
+ public void setNomComplet(String nomComplet) { this.nomComplet = nomComplet; }
+
+ public String getEmail() { return email; }
+ public void setEmail(String email) { this.email = email; }
+ }
+
+ public static class Filtres {
+ private String nom;
+ private String type;
+ private String statut;
+ private String region;
+ private String forfait;
+ private String alerteQuota;
+ private String alerteExpiration;
+ private String statutSouscription;
+
+ // Getters et setters
+ public String getNom() { return nom; }
+ public void setNom(String nom) { this.nom = nom; }
+
+ public String getType() { return type; }
+ public void setType(String type) { this.type = type; }
+
+ public String getStatut() { return statut; }
+ public void setStatut(String statut) { this.statut = statut; }
+
+ public String getRegion() { return region; }
+ public void setRegion(String region) { this.region = region; }
+
+ public String getForfait() { return forfait; }
+ public void setForfait(String forfait) { this.forfait = forfait; }
+
+ public String getAlerteQuota() { return alerteQuota; }
+ public void setAlerteQuota(String alerteQuota) { this.alerteQuota = alerteQuota; }
+
+ public String getAlerteExpiration() { return alerteExpiration; }
+ public void setAlerteExpiration(String alerteExpiration) { this.alerteExpiration = alerteExpiration; }
+
+ public String getStatutSouscription() { return statutSouscription; }
+ public void setStatutSouscription(String statutSouscription) { this.statutSouscription = statutSouscription; }
+ }
+
+ public static class Statistiques {
+ private int totalEntites;
+ private int entitesActives;
+ private int totalMembres;
+ private String revenus;
+ private int souscriptionsExpirantes;
+ private int entitesQuotaAtteint;
+ private String formulairePopulaire;
+ private float tauxRenouvellement;
+ private int moyenneMembresParEntite;
+
+ // Getters et setters
+ public int getTotalEntites() { return totalEntites; }
+ public void setTotalEntites(int totalEntites) { this.totalEntites = totalEntites; }
+
+ public int getEntitesActives() { return entitesActives; }
+ public void setEntitesActives(int entitesActives) { this.entitesActives = entitesActives; }
+
+ public int getTotalMembres() { return totalMembres; }
+ public void setTotalMembres(int totalMembres) { this.totalMembres = totalMembres; }
+
+ public String getRevenus() { return revenus; }
+ public void setRevenus(String revenus) { this.revenus = revenus; }
+
+ public int getSouscriptionsExpirantes() { return souscriptionsExpirantes; }
+ public void setSouscriptionsExpirantes(int souscriptionsExpirantes) { this.souscriptionsExpirantes = souscriptionsExpirantes; }
+
+ public int getEntitesQuotaAtteint() { return entitesQuotaAtteint; }
+ public void setEntitesQuotaAtteint(int entitesQuotaAtteint) { this.entitesQuotaAtteint = entitesQuotaAtteint; }
+
+ public String getFormulairePopulaire() { return formulairePopulaire; }
+ public void setFormulairePopulaire(String formulairePopulaire) { this.formulairePopulaire = formulairePopulaire; }
+
+ public float getTauxRenouvellement() { return tauxRenouvellement; }
+ public void setTauxRenouvellement(float tauxRenouvellement) { this.tauxRenouvellement = tauxRenouvellement; }
+
+ public int getMoyenneMembresParEntite() { return moyenneMembresParEntite; }
+ public void setMoyenneMembresParEntite(int moyenneMembresParEntite) { this.moyenneMembresParEntite = moyenneMembresParEntite; }
+
+ public String getTauxRenouvellementFormat() {
+ return String.format("%.1f%%", tauxRenouvellement);
+ }
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/EvenementsBean.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/EvenementsBean.java
new file mode 100644
index 0000000..d122a27
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/EvenementsBean.java
@@ -0,0 +1,588 @@
+package dev.lions.unionflow.client.view;
+
+import jakarta.enterprise.context.SessionScoped;
+import jakarta.inject.Named;
+import jakarta.annotation.PostConstruct;
+import java.io.Serializable;
+import java.time.LocalDate;
+import java.time.LocalDateTime;
+import java.time.LocalTime;
+import java.time.format.DateTimeFormatter;
+import java.time.temporal.ChronoUnit;
+import java.util.ArrayList;
+import java.util.List;
+import java.util.stream.Collectors;
+import java.math.BigDecimal;
+
+@Named("evenementsBean")
+@SessionScoped
+public class EvenementsBean implements Serializable {
+
+ private static final long serialVersionUID = 1L;
+
+ private List tousLesEvenements;
+ private List evenementsFiltres;
+ private List evenementsSelectionnes;
+ private List evenementsProchains;
+ private Evenement evenementSelectionne;
+ private NouvelEvenement nouvelEvenement;
+ private Filtres filtres;
+ private StatistiquesEvenements statistiques;
+
+ @PostConstruct
+ public void init() {
+ initializeFiltres();
+ initializeStatistiques();
+ initializeEvenements();
+ initializeNouvelEvenement();
+ initializeEvenementsProchains();
+ appliquerFiltres();
+ }
+
+ private void initializeFiltres() {
+ filtres = new Filtres();
+ evenementsSelectionnes = new ArrayList<>();
+ }
+
+ private void initializeStatistiques() {
+ statistiques = new StatistiquesEvenements();
+ statistiques.setTotalEvenements(42);
+ statistiques.setEvenementsActifs(18);
+ statistiques.setParticipantsTotal(1247);
+ statistiques.setBudgetTotal("3 450 000 FCFA");
+ statistiques.setMoyenneParticipants(69);
+ }
+
+ private void initializeEvenements() {
+ tousLesEvenements = new ArrayList<>();
+
+ String[] titres = {
+ "Assemblée Générale Ordinaire", "Formation Leadership", "Action Sociale Quartier Nord",
+ "Réunion Mensuelle Comité", "Conférence Développement Durable", "Collecte de Fonds",
+ "Journée Portes Ouvertes", "Atelier Gestion Financière", "Campagne Sensibilisation",
+ "Séminaire Jeunes Leaders", "Action Humanitaire", "Réunion Conseil Administration",
+ "Formation Premiers Secours", "Festival Culturel", "Réunion Coordination Régionale"
+ };
+
+ String[] types = {
+ "ASSEMBLEE_GENERALE", "FORMATION", "ACTION_SOCIALE", "REUNION", "FORMATION",
+ "ACTION_SOCIALE", "EVENEMENT_FESTIF", "FORMATION", "ACTION_SOCIALE", "FORMATION",
+ "ACTION_SOCIALE", "REUNION", "FORMATION", "EVENEMENT_FESTIF", "REUNION"
+ };
+
+ String[] statuts = {
+ "PLANIFIE", "PLANIFIE", "EN_COURS", "TERMINE", "PLANIFIE",
+ "PLANIFIE", "TERMINE", "PLANIFIE", "EN_COURS", "PLANIFIE",
+ "TERMINE", "PLANIFIE", "PLANIFIE", "TERMINE", "PLANIFIE"
+ };
+
+ String[] priorites = {
+ "CRITIQUE", "ELEVEE", "NORMALE", "NORMALE", "ELEVEE",
+ "NORMALE", "FAIBLE", "NORMALE", "ELEVEE", "NORMALE",
+ "CRITIQUE", "NORMALE", "FAIBLE", "FAIBLE", "NORMALE"
+ };
+
+ String[] lieux = {
+ "Salle Principale", "Centre Formation", "Quartier Nord", "Salle Réunion A",
+ "Auditorium Central", "Place Publique", "Hall d'Accueil", "Salle Formation B",
+ "Centre-Ville", "Campus Universitaire", "Zone Rurale", "Salle Conseil",
+ "Centre Médical", "Parc Municipal", "Siège Régional"
+ };
+
+ String[] organisateurs = {
+ "Marie Kouassi", "Paul Traoré", "Fatou Sanogo", "Jean Ouattara", "Aissata Koné",
+ "Ibrahim Touré", "Aminata Bakayoko", "Yves Koffi", "Mariam Coulibaly", "Seydou Cissé",
+ "Adjoa Mensah", "Kwame Asante", "Ama Gyamfi", "Kofi Adjei", "Ahmed Diallo"
+ };
+
+ for (int i = 0; i < titres.length; i++) {
+ Evenement evenement = new Evenement();
+ evenement.setId((long) (i + 1));
+ evenement.setTitre(titres[i]);
+ evenement.setType(types[i]);
+ evenement.setStatut(statuts[i]);
+ evenement.setPriorite(priorites[i]);
+ evenement.setLieu(lieux[i]);
+ evenement.setAdresse("Adresse " + lieux[i] + ", Ville");
+ evenement.setOrganisateur(organisateurs[i]);
+ evenement.setOrganisateurEmail(organisateurs[i].toLowerCase().replace(" ", ".") + "@unionflow.app");
+
+ // Dates aléatoires
+ LocalDate baseDate = LocalDate.now().plusDays(i * 3 - 15);
+ evenement.setDateDebut(baseDate);
+ evenement.setDateFin(baseDate.plusDays(i % 3 == 0 ? 1 : 0));
+ evenement.setHeureDebut(LocalTime.of(9 + (i % 8), 0));
+ evenement.setHeureFin(LocalTime.of(11 + (i % 8), 30));
+
+ // Participants et capacité
+ int capacite = 50 + (i * 10);
+ int inscrits = (int) (capacite * (0.3 + (i * 0.05) % 0.7));
+ evenement.setCapaciteMax(capacite);
+ evenement.setParticipantsInscrits(inscrits);
+
+ // Budget
+ BigDecimal budget = new BigDecimal(100000 + (i * 25000));
+ evenement.setBudget(budget);
+
+ // Description
+ evenement.setDescription("Description détaillée pour " + titres[i] + " avec objectifs et programme.");
+
+ tousLesEvenements.add(evenement);
+ }
+ }
+
+ private void initializeEvenementsProchains() {
+ evenementsProchains = tousLesEvenements.stream()
+ .filter(e -> e.getDateDebut().isAfter(LocalDate.now()) || e.getDateDebut().equals(LocalDate.now()))
+ .filter(e -> !e.getStatut().equals("ANNULE") && !e.getStatut().equals("TERMINE"))
+ .sorted((e1, e2) -> e1.getDateDebut().compareTo(e2.getDateDebut()))
+ .limit(6)
+ .collect(Collectors.toList());
+ }
+
+ private void initializeNouvelEvenement() {
+ nouvelEvenement = new NouvelEvenement();
+ nouvelEvenement.setPriorite("NORMALE");
+ nouvelEvenement.setDateDebut(LocalDate.now().plusWeeks(1));
+ }
+
+ private void appliquerFiltres() {
+ evenementsFiltres = tousLesEvenements.stream()
+ .filter(this::appliquerFiltre)
+ .collect(Collectors.toList());
+ }
+
+ private boolean appliquerFiltre(Evenement evenement) {
+ if (filtres.getTitre() != null && !filtres.getTitre().trim().isEmpty()) {
+ if (!evenement.getTitre().toLowerCase().contains(filtres.getTitre().toLowerCase())) {
+ return false;
+ }
+ }
+
+ if (filtres.getType() != null && !filtres.getType().trim().isEmpty()) {
+ if (!evenement.getType().equals(filtres.getType())) {
+ return false;
+ }
+ }
+
+ if (filtres.getStatut() != null && !filtres.getStatut().trim().isEmpty()) {
+ if (!evenement.getStatut().equals(filtres.getStatut())) {
+ return false;
+ }
+ }
+
+ if (filtres.getOrganisateur() != null && !filtres.getOrganisateur().trim().isEmpty()) {
+ if (!evenement.getOrganisateur().toLowerCase().contains(filtres.getOrganisateur().toLowerCase())) {
+ return false;
+ }
+ }
+
+ if (filtres.getPriorite() != null && !filtres.getPriorite().trim().isEmpty()) {
+ if (!evenement.getPriorite().equals(filtres.getPriorite())) {
+ return false;
+ }
+ }
+
+ if (filtres.getDateDebut() != null) {
+ if (evenement.getDateDebut().isBefore(filtres.getDateDebut())) {
+ return false;
+ }
+ }
+
+ if (filtres.getDateFin() != null) {
+ if (evenement.getDateDebut().isAfter(filtres.getDateFin())) {
+ return false;
+ }
+ }
+
+ return true;
+ }
+
+ // Actions
+ public void rechercher() {
+ appliquerFiltres();
+ }
+
+ public void reinitialiserFiltres() {
+ filtres = new Filtres();
+ appliquerFiltres();
+ }
+
+ public void creerEvenement() {
+ Evenement nouvelEvt = new Evenement();
+ nouvelEvt.setId((long) (tousLesEvenements.size() + 1));
+ nouvelEvt.setTitre(nouvelEvenement.getTitre());
+ nouvelEvt.setType(nouvelEvenement.getType());
+ nouvelEvt.setDateDebut(nouvelEvenement.getDateDebut());
+ nouvelEvt.setDateFin(nouvelEvenement.getDateFin());
+ nouvelEvt.setLieu(nouvelEvenement.getLieu());
+ nouvelEvt.setAdresse(nouvelEvenement.getAdresse());
+ nouvelEvt.setCapaciteMax(nouvelEvenement.getCapaciteMax());
+ nouvelEvt.setBudget(nouvelEvenement.getBudget());
+ nouvelEvt.setDescription(nouvelEvenement.getDescription());
+ nouvelEvt.setPriorite(nouvelEvenement.getPriorite());
+ nouvelEvt.setOrganisateur(nouvelEvenement.getOrganisateur());
+ nouvelEvt.setStatut("PLANIFIE");
+ nouvelEvt.setParticipantsInscrits(0);
+ nouvelEvt.setHeureDebut(LocalTime.of(9, 0));
+ nouvelEvt.setHeureFin(LocalTime.of(17, 0));
+
+ tousLesEvenements.add(nouvelEvt);
+ appliquerFiltres();
+ initializeEvenementsProchains();
+
+ System.out.println("Nouvel événement créé: " + nouvelEvt.getTitre());
+ initializeNouvelEvenement();
+ }
+
+ public String gererParticipants() {
+ return "/pages/admin/evenements/participants?id=" + evenementSelectionne.getId() + "&faces-redirect=true";
+ }
+
+ public void envoyerInvitations() {
+ System.out.println("Invitations envoyées pour: " + evenementSelectionne.getTitre());
+ }
+
+ public String voirRapports() {
+ return "/pages/admin/evenements/rapports?id=" + evenementSelectionne.getId() + "&faces-redirect=true";
+ }
+
+ public void annulerEvenement() {
+ if (evenementSelectionne != null) {
+ evenementSelectionne.setStatut("ANNULE");
+ System.out.println("Événement annulé: " + evenementSelectionne.getTitre());
+ appliquerFiltres();
+ initializeEvenementsProchains();
+ }
+ }
+
+ public void dupliquerEvenement() {
+ if (evenementSelectionne != null) {
+ Evenement copie = new Evenement();
+ copie.setId((long) (tousLesEvenements.size() + 1));
+ copie.setTitre(evenementSelectionne.getTitre() + " (Copie)");
+ copie.setType(evenementSelectionne.getType());
+ copie.setLieu(evenementSelectionne.getLieu());
+ copie.setAdresse(evenementSelectionne.getAdresse());
+ copie.setCapaciteMax(evenementSelectionne.getCapaciteMax());
+ copie.setBudget(evenementSelectionne.getBudget());
+ copie.setDescription(evenementSelectionne.getDescription());
+ copie.setPriorite(evenementSelectionne.getPriorite());
+ copie.setOrganisateur(evenementSelectionne.getOrganisateur());
+ copie.setStatut("PLANIFIE");
+ copie.setParticipantsInscrits(0);
+ copie.setDateDebut(LocalDate.now().plusWeeks(2));
+ copie.setDateFin(evenementSelectionne.getDateFin());
+ copie.setHeureDebut(evenementSelectionne.getHeureDebut());
+ copie.setHeureFin(evenementSelectionne.getHeureFin());
+
+ tousLesEvenements.add(copie);
+ appliquerFiltres();
+ System.out.println("Événement dupliqué: " + copie.getTitre());
+ }
+ }
+
+ public void exporterEvenements() {
+ System.out.println("Export de " + evenementsFiltres.size() + " événements");
+ }
+
+ public void exporterExcel() {
+ System.out.println("Export Excel de " + evenementsFiltres.size() + " événements");
+ }
+
+ // Getters et Setters
+ public List getTousLesEvenements() { return tousLesEvenements; }
+ public void setTousLesEvenements(List tousLesEvenements) { this.tousLesEvenements = tousLesEvenements; }
+
+ public List getEvenementsFiltres() { return evenementsFiltres; }
+ public void setEvenementsFiltres(List evenementsFiltres) { this.evenementsFiltres = evenementsFiltres; }
+
+ public List getEvenementsSelectionnes() { return evenementsSelectionnes; }
+ public void setEvenementsSelectionnes(List evenementsSelectionnes) { this.evenementsSelectionnes = evenementsSelectionnes; }
+
+ public List getEvenementsProchains() { return evenementsProchains; }
+ public void setEvenementsProchains(List evenementsProchains) { this.evenementsProchains = evenementsProchains; }
+
+ public Evenement getEvenementSelectionne() { return evenementSelectionne; }
+ public void setEvenementSelectionne(Evenement evenementSelectionne) { this.evenementSelectionne = evenementSelectionne; }
+
+ public NouvelEvenement getNouvelEvenement() { return nouvelEvenement; }
+ public void setNouvelEvenement(NouvelEvenement nouvelEvenement) { this.nouvelEvenement = nouvelEvenement; }
+
+ public Filtres getFiltres() { return filtres; }
+ public void setFiltres(Filtres filtres) { this.filtres = filtres; }
+
+ public StatistiquesEvenements getStatistiques() { return statistiques; }
+ public void setStatistiques(StatistiquesEvenements statistiques) { this.statistiques = statistiques; }
+
+ // Classes internes
+ public static class Evenement {
+ private Long id;
+ private String titre;
+ private String description;
+ private String type;
+ private String statut;
+ private String priorite;
+ private LocalDate dateDebut;
+ private LocalDate dateFin;
+ private LocalTime heureDebut;
+ private LocalTime heureFin;
+ private String lieu;
+ private String adresse;
+ private String organisateur;
+ private String organisateurEmail;
+ private int capaciteMax;
+ private int participantsInscrits;
+ private BigDecimal budget;
+
+ // Getters et setters
+ public Long getId() { return id; }
+ public void setId(Long id) { this.id = id; }
+
+ public String getTitre() { return titre; }
+ public void setTitre(String titre) { this.titre = titre; }
+
+ public String getDescription() { return description; }
+ public void setDescription(String description) { this.description = description; }
+
+ public String getType() { return type; }
+ public void setType(String type) { this.type = type; }
+
+ public String getStatut() { return statut; }
+ public void setStatut(String statut) { this.statut = statut; }
+
+ public String getPriorite() { return priorite; }
+ public void setPriorite(String priorite) { this.priorite = priorite; }
+
+ public LocalDate getDateDebut() { return dateDebut; }
+ public void setDateDebut(LocalDate dateDebut) { this.dateDebut = dateDebut; }
+
+ public LocalDate getDateFin() { return dateFin; }
+ public void setDateFin(LocalDate dateFin) { this.dateFin = dateFin; }
+
+ public LocalTime getHeureDebut() { return heureDebut; }
+ public void setHeureDebut(LocalTime heureDebut) { this.heureDebut = heureDebut; }
+
+ public LocalTime getHeureFin() { return heureFin; }
+ public void setHeureFin(LocalTime heureFin) { this.heureFin = heureFin; }
+
+ public String getLieu() { return lieu; }
+ public void setLieu(String lieu) { this.lieu = lieu; }
+
+ public String getAdresse() { return adresse; }
+ public void setAdresse(String adresse) { this.adresse = adresse; }
+
+ public String getOrganisateur() { return organisateur; }
+ public void setOrganisateur(String organisateur) { this.organisateur = organisateur; }
+
+ public String getOrganisateurEmail() { return organisateurEmail; }
+ public void setOrganisateurEmail(String organisateurEmail) { this.organisateurEmail = organisateurEmail; }
+
+ public int getCapaciteMax() { return capaciteMax; }
+ public void setCapaciteMax(int capaciteMax) { this.capaciteMax = capaciteMax; }
+
+ public int getParticipantsInscrits() { return participantsInscrits; }
+ public void setParticipantsInscrits(int participantsInscrits) { this.participantsInscrits = participantsInscrits; }
+
+ public BigDecimal getBudget() { return budget; }
+ public void setBudget(BigDecimal budget) { this.budget = budget; }
+
+ // Propriétés dérivées
+ public String getTypeLibelle() {
+ return switch (type) {
+ case "REUNION" -> "Réunion";
+ case "FORMATION" -> "Formation";
+ case "ACTION_SOCIALE" -> "Action Sociale";
+ case "ASSEMBLEE_GENERALE" -> "Assemblée Générale";
+ case "EVENEMENT_FESTIF" -> "Événement Festif";
+ default -> type;
+ };
+ }
+
+ public String getTypeSeverity() {
+ return switch (type) {
+ case "REUNION" -> "info";
+ case "FORMATION" -> "success";
+ case "ACTION_SOCIALE" -> "warning";
+ case "ASSEMBLEE_GENERALE" -> "danger";
+ case "EVENEMENT_FESTIF" -> "secondary";
+ default -> "primary";
+ };
+ }
+
+ public String getTypeIcon() {
+ return switch (type) {
+ case "REUNION" -> "pi-users";
+ case "FORMATION" -> "pi-book";
+ case "ACTION_SOCIALE" -> "pi-heart";
+ case "ASSEMBLEE_GENERALE" -> "pi-sitemap";
+ case "EVENEMENT_FESTIF" -> "pi-star";
+ default -> "pi-calendar";
+ };
+ }
+
+ public String getStatutSeverity() {
+ return switch (statut) {
+ case "PLANIFIE" -> "info";
+ case "EN_COURS" -> "warning";
+ case "TERMINE" -> "success";
+ case "ANNULE" -> "danger";
+ default -> "secondary";
+ };
+ }
+
+ public String getStatutIcon() {
+ return switch (statut) {
+ case "PLANIFIE" -> "pi-clock";
+ case "EN_COURS" -> "pi-play";
+ case "TERMINE" -> "pi-check";
+ case "ANNULE" -> "pi-ban";
+ default -> "pi-circle";
+ };
+ }
+
+ public String getPrioriteSeverity() {
+ return switch (priorite) {
+ case "FAIBLE" -> "secondary";
+ case "NORMALE" -> "info";
+ case "ELEVEE" -> "warning";
+ case "CRITIQUE" -> "danger";
+ default -> "primary";
+ };
+ }
+
+ public String getDateDebutFormatee() {
+ if (dateDebut == null) return "";
+ return dateDebut.format(DateTimeFormatter.ofPattern("dd/MM/yyyy"));
+ }
+
+ public String getHeureDebutFormatee() {
+ if (heureDebut == null) return "";
+ return heureDebut.format(DateTimeFormatter.ofPattern("HH:mm"));
+ }
+
+ public String getHeureFinFormatee() {
+ if (heureFin == null) return "";
+ return heureFin.format(DateTimeFormatter.ofPattern("HH:mm"));
+ }
+
+ public String getBudgetFormatte() {
+ if (budget == null) return "";
+ return String.format("%,.0f FCFA", budget);
+ }
+
+ public int getTauxInscription() {
+ if (capaciteMax == 0) return 0;
+ return (int) ((double) participantsInscrits / capaciteMax * 100);
+ }
+
+ public long getJoursRestants() {
+ if (dateDebut == null) return 0;
+ return ChronoUnit.DAYS.between(LocalDate.now(), dateDebut);
+ }
+ }
+
+ public static class NouvelEvenement {
+ private String titre;
+ private String description;
+ private String type;
+ private String priorite;
+ private LocalDate dateDebut;
+ private LocalDate dateFin;
+ private String lieu;
+ private String adresse;
+ private String organisateur;
+ private Integer capaciteMax;
+ private BigDecimal budget;
+
+ // Getters et setters
+ public String getTitre() { return titre; }
+ public void setTitre(String titre) { this.titre = titre; }
+
+ public String getDescription() { return description; }
+ public void setDescription(String description) { this.description = description; }
+
+ public String getType() { return type; }
+ public void setType(String type) { this.type = type; }
+
+ public String getPriorite() { return priorite; }
+ public void setPriorite(String priorite) { this.priorite = priorite; }
+
+ public LocalDate getDateDebut() { return dateDebut; }
+ public void setDateDebut(LocalDate dateDebut) { this.dateDebut = dateDebut; }
+
+ public LocalDate getDateFin() { return dateFin; }
+ public void setDateFin(LocalDate dateFin) { this.dateFin = dateFin; }
+
+ public String getLieu() { return lieu; }
+ public void setLieu(String lieu) { this.lieu = lieu; }
+
+ public String getAdresse() { return adresse; }
+ public void setAdresse(String adresse) { this.adresse = adresse; }
+
+ public String getOrganisateur() { return organisateur; }
+ public void setOrganisateur(String organisateur) { this.organisateur = organisateur; }
+
+ public Integer getCapaciteMax() { return capaciteMax; }
+ public void setCapaciteMax(Integer capaciteMax) { this.capaciteMax = capaciteMax; }
+
+ public BigDecimal getBudget() { return budget; }
+ public void setBudget(BigDecimal budget) { this.budget = budget; }
+ }
+
+ public static class Filtres {
+ private String titre;
+ private String type;
+ private String statut;
+ private String organisateur;
+ private String priorite;
+ private LocalDate dateDebut;
+ private LocalDate dateFin;
+
+ // Getters et setters
+ public String getTitre() { return titre; }
+ public void setTitre(String titre) { this.titre = titre; }
+
+ public String getType() { return type; }
+ public void setType(String type) { this.type = type; }
+
+ public String getStatut() { return statut; }
+ public void setStatut(String statut) { this.statut = statut; }
+
+ public String getOrganisateur() { return organisateur; }
+ public void setOrganisateur(String organisateur) { this.organisateur = organisateur; }
+
+ public String getPriorite() { return priorite; }
+ public void setPriorite(String priorite) { this.priorite = priorite; }
+
+ public LocalDate getDateDebut() { return dateDebut; }
+ public void setDateDebut(LocalDate dateDebut) { this.dateDebut = dateDebut; }
+
+ public LocalDate getDateFin() { return dateFin; }
+ public void setDateFin(LocalDate dateFin) { this.dateFin = dateFin; }
+ }
+
+ public static class StatistiquesEvenements {
+ private int totalEvenements;
+ private int evenementsActifs;
+ private int participantsTotal;
+ private String budgetTotal;
+ private int moyenneParticipants;
+
+ // Getters et setters
+ public int getTotalEvenements() { return totalEvenements; }
+ public void setTotalEvenements(int totalEvenements) { this.totalEvenements = totalEvenements; }
+
+ public int getEvenementsActifs() { return evenementsActifs; }
+ public void setEvenementsActifs(int evenementsActifs) { this.evenementsActifs = evenementsActifs; }
+
+ public int getParticipantsTotal() { return participantsTotal; }
+ public void setParticipantsTotal(int participantsTotal) { this.participantsTotal = participantsTotal; }
+
+ public String getBudgetTotal() { return budgetTotal; }
+ public void setBudgetTotal(String budgetTotal) { this.budgetTotal = budgetTotal; }
+
+ public int getMoyenneParticipants() { return moyenneParticipants; }
+ public void setMoyenneParticipants(int moyenneParticipants) { this.moyenneParticipants = moyenneParticipants; }
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/FormulaireBean.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/FormulaireBean.java
new file mode 100644
index 0000000..dd317f4
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/FormulaireBean.java
@@ -0,0 +1,261 @@
+package dev.lions.unionflow.client.view;
+
+import dev.lions.unionflow.client.dto.FormulaireDTO;
+import dev.lions.unionflow.client.dto.SouscriptionDTO;
+import jakarta.enterprise.context.RequestScoped;
+import jakarta.inject.Named;
+import java.io.Serializable;
+import java.math.BigDecimal;
+import java.util.ArrayList;
+import java.util.List;
+
+@Named("formulaireBean")
+@RequestScoped
+public class FormulaireBean implements Serializable {
+
+ private static final long serialVersionUID = 1L;
+
+ private List formulaires;
+ private List formulairesPopulaires;
+ private FormulaireDTO formulaireSelectionne;
+ private SouscriptionDTO.TypeFacturation typeFacturationSelectionne = SouscriptionDTO.TypeFacturation.MENSUEL;
+
+ // Filtres
+ private Integer membresMax;
+ private BigDecimal budgetMax;
+ private String categorieFiltre = "ALL";
+
+ public FormulaireBean() {
+ initializeFormulaires();
+ }
+
+ private void initializeFormulaires() {
+ formulaires = new ArrayList<>();
+
+ // Formulaire STARTER - Pour les petites associations
+ FormulaireDTO starter = new FormulaireDTO();
+ starter.setId(1L);
+ starter.setNom("Starter");
+ starter.setDescription("Parfait pour les associations débutantes");
+ starter.setQuotaMaxMembres(100);
+ starter.setPrixMensuel(new BigDecimal("2000")); // 2K FCFA
+ starter.setPrixAnnuel(new BigDecimal("20000")); // 20K FCFA (2 mois gratuits)
+ starter.setCouleurTheme("bg-blue-500");
+ starter.setIconeFormulaire("pi-star");
+ starter.setGestionMembres(true);
+ starter.setGestionCotisations(true);
+ starter.setGestionEvenements(false);
+ starter.setGestionAides(false);
+ starter.setRapportsAvances(false);
+ starter.setNotificationsEmail(true);
+ formulaires.add(starter);
+
+ // Formulaire STANDARD - Pour les associations moyennes
+ FormulaireDTO standard = new FormulaireDTO();
+ standard.setId(2L);
+ standard.setNom("Standard");
+ standard.setDescription("Idéal pour les associations en croissance");
+ standard.setQuotaMaxMembres(200);
+ standard.setPrixMensuel(new BigDecimal("3000")); // 3K FCFA
+ standard.setPrixAnnuel(new BigDecimal("30000")); // 30K FCFA (2 mois gratuits)
+ standard.setCouleurTheme("bg-green-500");
+ standard.setIconeFormulaire("pi-users");
+ standard.setRecommande(true);
+ standard.setGestionMembres(true);
+ standard.setGestionCotisations(true);
+ standard.setGestionEvenements(true);
+ standard.setGestionAides(true);
+ standard.setRapportsAvances(false);
+ standard.setNotificationsEmail(true);
+ standard.setNotificationsSMS(false);
+ standard.setGestionDocuments(true);
+ formulaires.add(standard);
+
+ // Formulaire PREMIUM - Pour les grandes associations
+ FormulaireDTO premium = new FormulaireDTO();
+ premium.setId(3L);
+ premium.setNom("Premium");
+ premium.setDescription("Solution complète pour les grandes organisations");
+ premium.setQuotaMaxMembres(500);
+ premium.setPrixMensuel(new BigDecimal("4000")); // 4K FCFA
+ premium.setPrixAnnuel(new BigDecimal("40000")); // 40K FCFA (2 mois gratuits)
+ premium.setCouleurTheme("bg-purple-500");
+ premium.setIconeFormulaire("pi-crown");
+ premium.setGestionMembres(true);
+ premium.setGestionCotisations(true);
+ premium.setGestionEvenements(true);
+ premium.setGestionAides(true);
+ premium.setRapportsAvances(true);
+ premium.setSupportPrioritaire(true);
+ premium.setSauvegardeAutomatique(true);
+ premium.setPersonnalisationAvancee(true);
+ premium.setIntegrationPaiement(true);
+ premium.setNotificationsEmail(true);
+ premium.setNotificationsSMS(true);
+ premium.setGestionDocuments(true);
+ formulaires.add(premium);
+
+ // Formulaire CRISTAL - Pour les très grandes organisations
+ FormulaireDTO cristal = new FormulaireDTO();
+ cristal.setId(4L);
+ cristal.setNom("Cristal");
+ cristal.setDescription("Solution premium pour les fédérations et grandes entités");
+ cristal.setQuotaMaxMembres(2000);
+ cristal.setPrixMensuel(new BigDecimal("5000")); // 5K FCFA
+ cristal.setPrixAnnuel(new BigDecimal("50000")); // 50K FCFA (2 mois gratuits)
+ cristal.setCouleurTheme("bg-indigo-500");
+ cristal.setIconeFormulaire("pi-diamond");
+ cristal.setGestionMembres(true);
+ cristal.setGestionCotisations(true);
+ cristal.setGestionEvenements(true);
+ cristal.setGestionAides(true);
+ cristal.setRapportsAvances(true);
+ cristal.setSupportPrioritaire(true);
+ cristal.setSauvegardeAutomatique(true);
+ cristal.setPersonnalisationAvancee(true);
+ cristal.setIntegrationPaiement(true);
+ cristal.setNotificationsEmail(true);
+ cristal.setNotificationsSMS(true);
+ cristal.setGestionDocuments(true);
+ formulaires.add(cristal);
+
+ // Définir les formulaires populaires (Standard et Premium)
+ formulairesPopulaires = new ArrayList<>();
+ formulairesPopulaires.add(standard);
+ formulairesPopulaires.add(premium);
+ }
+
+ public void selectionnerFormulaire(FormulaireDTO formulaire) {
+ this.formulaireSelectionne = formulaire;
+ }
+
+ public String procederSouscription() {
+ if (formulaireSelectionne != null) {
+ // Rediriger vers la page de souscription avec les paramètres
+ return "/pages/secure/souscription/checkout?formulaire=" +
+ formulaireSelectionne.getId() +
+ "&facturation=" + typeFacturationSelectionne.name() +
+ "&faces-redirect=true";
+ }
+ return null;
+ }
+
+ public String voirDetailsFormulaire(FormulaireDTO formulaire) {
+ return "/pages/public/formulaires/details?id=" + formulaire.getId() + "&faces-redirect=true";
+ }
+
+ public List getFormulairesFiltres() {
+ return formulaires.stream()
+ .filter(f -> {
+ // Filtre par nombre de membres
+ if (membresMax != null && f.getQuotaMaxMembres() > membresMax) {
+ return false;
+ }
+
+ // Filtre par budget
+ if (budgetMax != null) {
+ BigDecimal prix = (typeFacturationSelectionne == SouscriptionDTO.TypeFacturation.MENSUEL)
+ ? f.getPrixMensuel() : f.getPrixAnnuel();
+ if (prix.compareTo(budgetMax) > 0) {
+ return false;
+ }
+ }
+
+ // Filtre par catégorie
+ if (!"ALL".equals(categorieFiltre)) {
+ switch (categorieFiltre) {
+ case "SMALL":
+ return f.getQuotaMaxMembres() <= 50;
+ case "MEDIUM":
+ return f.getQuotaMaxMembres() > 50 && f.getQuotaMaxMembres() <= 200;
+ case "LARGE":
+ return f.getQuotaMaxMembres() > 200;
+ }
+ }
+
+ return true;
+ })
+ .toList();
+ }
+
+ public void resetFiltres() {
+ membresMax = null;
+ budgetMax = null;
+ categorieFiltre = "ALL";
+ }
+
+ public String getPrixAffiche(FormulaireDTO formulaire) {
+ if (typeFacturationSelectionne == SouscriptionDTO.TypeFacturation.MENSUEL) {
+ return formulaire.getPrixMensuelFormat() + "/mois";
+ } else {
+ return formulaire.getPrixAnnuelFormat() + "/an";
+ }
+ }
+
+ public String getEconomieAffichee(FormulaireDTO formulaire) {
+ if (typeFacturationSelectionne == SouscriptionDTO.TypeFacturation.ANNUEL) {
+ int pourcentage = formulaire.getPourcentageEconomie();
+ if (pourcentage > 0) {
+ return "Économisez " + pourcentage + "%";
+ }
+ }
+ return "";
+ }
+
+ public boolean isFormulaireFonctionnaliteActive(FormulaireDTO formulaire, String fonctionnalite) {
+ switch (fonctionnalite.toLowerCase()) {
+ case "membres":
+ return formulaire.isGestionMembres();
+ case "cotisations":
+ return formulaire.isGestionCotisations();
+ case "evenements":
+ return formulaire.isGestionEvenements();
+ case "aides":
+ return formulaire.isGestionAides();
+ case "rapports":
+ return formulaire.isRapportsAvances();
+ case "support":
+ return formulaire.isSupportPrioritaire();
+ case "sauvegarde":
+ return formulaire.isSauvegardeAutomatique();
+ case "personnalisation":
+ return formulaire.isPersonnalisationAvancee();
+ case "paiement":
+ return formulaire.isIntegrationPaiement();
+ case "email":
+ return formulaire.isNotificationsEmail();
+ case "sms":
+ return formulaire.isNotificationsSMS();
+ case "documents":
+ return formulaire.isGestionDocuments();
+ default:
+ return false;
+ }
+ }
+
+ public String getComparaisonClasse() {
+ return formulaires.size() <= 3 ? "col-12 md:col-4" : "col-12 md:col-6 lg:col-3";
+ }
+
+ // Getters et Setters
+ public List getFormulaires() { return formulaires; }
+ public void setFormulaires(List formulaires) { this.formulaires = formulaires; }
+
+ public List getFormulairesPopulaires() { return formulairesPopulaires; }
+ public void setFormulairesPopulaires(List formulairesPopulaires) { this.formulairesPopulaires = formulairesPopulaires; }
+
+ public FormulaireDTO getFormulaireSelectionne() { return formulaireSelectionne; }
+ public void setFormulaireSelectionne(FormulaireDTO formulaireSelectionne) { this.formulaireSelectionne = formulaireSelectionne; }
+
+ public SouscriptionDTO.TypeFacturation getTypeFacturationSelectionne() { return typeFacturationSelectionne; }
+ public void setTypeFacturationSelectionne(SouscriptionDTO.TypeFacturation typeFacturationSelectionne) { this.typeFacturationSelectionne = typeFacturationSelectionne; }
+
+ public Integer getMembresMax() { return membresMax; }
+ public void setMembresMax(Integer membresMax) { this.membresMax = membresMax; }
+
+ public BigDecimal getBudgetMax() { return budgetMax; }
+ public void setBudgetMax(BigDecimal budgetMax) { this.budgetMax = budgetMax; }
+
+ public String getCategorieFiltre() { return categorieFiltre; }
+ public void setCategorieFiltre(String categorieFiltre) { this.categorieFiltre = categorieFiltre; }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/GuestPreferences.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/GuestPreferences.java
new file mode 100644
index 0000000..edfd2b7
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/GuestPreferences.java
@@ -0,0 +1,146 @@
+package dev.lions.unionflow.client.view;
+
+import jakarta.enterprise.context.SessionScoped;
+import jakarta.inject.Named;
+import java.io.Serializable;
+import java.util.ArrayList;
+import java.util.List;
+
+@Named("guestPreferences")
+@SessionScoped
+public class GuestPreferences implements Serializable {
+
+ private static final long serialVersionUID = 1L;
+
+ private String theme = "blue-light";
+ private String layout = "light";
+ private String componentTheme = "blue-light";
+ private String darkMode = "light";
+ private String menuMode = "layout-sidebar";
+ private String topbarTheme = "light";
+ private String menuTheme = "light";
+ private String inputStyle = "outlined";
+ private boolean lightLogo = false;
+
+ public String getTheme() {
+ return theme;
+ }
+
+ public void setTheme(String theme) {
+ this.theme = theme;
+ }
+
+ public String getLayout() {
+ return layout;
+ }
+
+ public void setLayout(String layout) {
+ this.layout = layout;
+ }
+
+ public String getComponentTheme() {
+ return componentTheme;
+ }
+
+ public void setComponentTheme(String componentTheme) {
+ this.componentTheme = componentTheme;
+ }
+
+ public String getDarkMode() {
+ return darkMode;
+ }
+
+ public void setDarkMode(String darkMode) {
+ this.darkMode = darkMode;
+ this.lightLogo = "dark".equals(darkMode);
+ }
+
+ public String getMenuMode() {
+ return menuMode;
+ }
+
+ public void setMenuMode(String menuMode) {
+ this.menuMode = menuMode;
+ }
+
+ public String getTopbarTheme() {
+ return topbarTheme;
+ }
+
+ public void setTopbarTheme(String topbarTheme) {
+ this.topbarTheme = topbarTheme;
+ }
+
+ public String getMenuTheme() {
+ return menuTheme;
+ }
+
+ public void setMenuTheme(String menuTheme) {
+ this.menuTheme = menuTheme;
+ }
+
+ public String getInputStyle() {
+ return inputStyle;
+ }
+
+ public void setInputStyle(String inputStyle) {
+ this.inputStyle = inputStyle;
+ }
+
+ public boolean isLightLogo() {
+ return lightLogo;
+ }
+
+ public void setLightLogo(boolean lightLogo) {
+ this.lightLogo = lightLogo;
+ }
+
+ public String getInputStyleClass() {
+ return "p-input-" + inputStyle;
+ }
+
+ public String getLayoutClass() {
+ return "layout-" + layout + " layout-theme-" + theme;
+ }
+
+ public List getComponentThemes() {
+ List themes = new ArrayList<>();
+ themes.add(new ComponentTheme("blue-light", "Blue", "#007ad9"));
+ themes.add(new ComponentTheme("green-light", "Green", "#28a745"));
+ themes.add(new ComponentTheme("orange-light", "Orange", "#fd7e14"));
+ themes.add(new ComponentTheme("purple-light", "Purple", "#6f42c1"));
+ themes.add(new ComponentTheme("pink-light", "Pink", "#e83e8c"));
+ themes.add(new ComponentTheme("indigo-light", "Indigo", "#6610f2"));
+ themes.add(new ComponentTheme("teal-light", "Teal", "#20c997"));
+ themes.add(new ComponentTheme("cyan-light", "Cyan", "#17a2b8"));
+ return themes;
+ }
+
+ public void onMenuTypeChange() {
+ // Called when menu type changes
+ }
+
+ public static class ComponentTheme {
+ private String file;
+ private String name;
+ private String color;
+
+ public ComponentTheme(String file, String name, String color) {
+ this.file = file;
+ this.name = name;
+ this.color = color;
+ }
+
+ public String getFile() {
+ return file;
+ }
+
+ public String getName() {
+ return name;
+ }
+
+ public String getColor() {
+ return color;
+ }
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/GuideBean.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/GuideBean.java
new file mode 100644
index 0000000..53e4317
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/GuideBean.java
@@ -0,0 +1,241 @@
+package dev.lions.unionflow.client.view;
+
+import jakarta.enterprise.context.SessionScoped;
+import jakarta.inject.Named;
+import java.io.Serializable;
+import java.util.*;
+import java.util.stream.Collectors;
+
+@Named("guideBean")
+@SessionScoped
+public class GuideBean implements Serializable {
+
+ private static final long serialVersionUID = 1L;
+
+ // Structure du guide
+ private List toutesSections;
+ private SectionGuide sectionCourante;
+ private String sectionActiveId = "default";
+ private int sectionActive = 0;
+
+ // Recherche
+ private String termeRecherche = "";
+
+ public GuideBean() {
+ initialiserSections();
+ sectionCourante = new SectionGuide("default", "Accueil", "", "", 0, false);
+ }
+
+ private void initialiserSections() {
+ toutesSections = new ArrayList<>();
+
+ // Section 1: Premiers pas
+ toutesSections.add(new SectionGuide("premiers-pas-connexion", "Se connecter", "Premiers Pas", "Apprendre à se connecter à UnionFlow", 5, false));
+ toutesSections.add(new SectionGuide("premiers-pas-interface", "Découvrir l'interface", "Premiers Pas", "Navigation et organisation de l'interface", 8, false));
+ toutesSections.add(new SectionGuide("premiers-pas-profil", "Configurer son profil", "Premiers Pas", "Personnaliser ses informations personnelles", 10, false));
+ toutesSections.add(new SectionGuide("premiers-pas-navigation", "Navigation dans le système", "Premiers Pas", "Utiliser les menus et raccourcis", 6, false));
+
+ // Section 2: Gestion des membres
+ toutesSections.add(new SectionGuide("membres-inscription", "Inscrire un membre", "Gestion Membres", "Processus d'inscription d'un nouveau membre", 12, false));
+ toutesSections.add(new SectionGuide("membres-modification", "Modifier un profil", "Gestion Membres", "Mettre à jour les informations d'un membre", 8, false));
+ toutesSections.add(new SectionGuide("membres-recherche", "Rechercher des membres", "Gestion Membres", "Utiliser les filtres de recherche avancée", 6, false));
+ toutesSections.add(new SectionGuide("membres-export", "Exporter la liste", "Gestion Membres", "Générer des exports Excel et PDF", 10, false));
+ toutesSections.add(new SectionGuide("membres-historique", "Consulter l'historique", "Gestion Membres", "Suivre les modifications et activités", 7, false));
+
+ // Section 3: Finances
+ toutesSections.add(new SectionGuide("finances-cotisations", "Gérer les cotisations", "Finances", "Configuration et suivi des cotisations", 15, false));
+ toutesSections.add(new SectionGuide("finances-paiements", "Enregistrer les paiements", "Finances", "Saisie manuelle et automatique", 12, false));
+ toutesSections.add(new SectionGuide("finances-relances", "Relances automatiques", "Finances", "Configuration des rappels de paiement", 10, false));
+ toutesSections.add(new SectionGuide("finances-rapports", "Rapports financiers", "Finances", "Générer des bilans et statistiques", 18, false));
+
+ // Section 4: Événements
+ toutesSections.add(new SectionGuide("events-creation", "Créer un événement", "Événements", "Planifier et organiser des événements", 15, false));
+ toutesSections.add(new SectionGuide("events-inscriptions", "Gérer les inscriptions", "Événements", "Suivre les participations", 10, false));
+ toutesSections.add(new SectionGuide("events-communication", "Communication événement", "Événements", "Envoyer invitations et rappels", 12, false));
+ toutesSections.add(new SectionGuide("events-bilan", "Bilan post-événement", "Événements", "Analyser la participation et satisfaction", 8, false));
+
+ // Section 5: Rapports
+ toutesSections.add(new SectionGuide("rapports-creation", "Créer des rapports", "Rapports", "Utiliser le générateur de rapports", 20, false));
+ toutesSections.add(new SectionGuide("rapports-tableaux", "Tableaux de bord", "Rapports", "Configurer ses indicateurs personnalisés", 15, false));
+ toutesSections.add(new SectionGuide("rapports-export", "Export et partage", "Rapports", "Distribuer les rapports aux parties prenantes", 10, false));
+
+ // Section 6: Administration
+ toutesSections.add(new SectionGuide("admin-utilisateurs", "Gestion des utilisateurs", "Administration", "Créer et gérer les comptes utilisateurs", 18, false));
+ toutesSections.add(new SectionGuide("admin-permissions", "Rôles et permissions", "Administration", "Configuration des droits d'accès", 22, false));
+ toutesSections.add(new SectionGuide("admin-parametres", "Paramètres système", "Administration", "Configuration générale de l'application", 25, false));
+ toutesSections.add(new SectionGuide("admin-sauvegarde", "Sauvegarde et sécurité", "Administration", "Protéger et sauvegarder les données", 15, false));
+ toutesSections.add(new SectionGuide("admin-audit", "Journal d'audit", "Administration", "Surveiller l'activité et la sécurité", 12, false));
+ }
+
+ // Getters pour les sections par catégorie
+ public List getSectionsPremiersPas() {
+ return toutesSections.stream()
+ .filter(s -> "Premiers Pas".equals(s.getCategorie()))
+ .collect(Collectors.toList());
+ }
+
+ public List getSectionsMembres() {
+ return toutesSections.stream()
+ .filter(s -> "Gestion Membres".equals(s.getCategorie()))
+ .collect(Collectors.toList());
+ }
+
+ public List getSectionsFinances() {
+ return toutesSections.stream()
+ .filter(s -> "Finances".equals(s.getCategorie()))
+ .collect(Collectors.toList());
+ }
+
+ public List getSectionsEvenements() {
+ return toutesSections.stream()
+ .filter(s -> "Événements".equals(s.getCategorie()))
+ .collect(Collectors.toList());
+ }
+
+ public List getSectionsRapports() {
+ return toutesSections.stream()
+ .filter(s -> "Rapports".equals(s.getCategorie()))
+ .collect(Collectors.toList());
+ }
+
+ public List getSectionsAdmin() {
+ return toutesSections.stream()
+ .filter(s -> "Administration".equals(s.getCategorie()))
+ .collect(Collectors.toList());
+ }
+
+ // Statistiques de progression
+ public int getTotalSections() {
+ return toutesSections.size();
+ }
+
+ public int getSectionsLues() {
+ return (int) toutesSections.stream().filter(SectionGuide::isLu).count();
+ }
+
+ public int getPourcentageProgression() {
+ if (getTotalSections() == 0) return 0;
+ return (getSectionsLues() * 100) / getTotalSections();
+ }
+
+ // Navigation
+ public void naviguerVers(String sectionId) {
+ this.sectionActiveId = sectionId;
+ this.sectionCourante = toutesSections.stream()
+ .filter(s -> s.getId().equals(sectionId))
+ .findFirst()
+ .orElse(new SectionGuide("default", "Accueil", "", "", 0, false));
+ }
+
+ public void sectionPrecedente() {
+ int index = trouverIndexSection(sectionActiveId);
+ if (index > 0) {
+ naviguerVers(toutesSections.get(index - 1).getId());
+ }
+ }
+
+ public void sectionSuivante() {
+ int index = trouverIndexSection(sectionActiveId);
+ if (index < toutesSections.size() - 1) {
+ naviguerVers(toutesSections.get(index + 1).getId());
+ }
+ }
+
+ public boolean isAPrecedent() {
+ return trouverIndexSection(sectionActiveId) > 0;
+ }
+
+ public boolean isASuivant() {
+ int index = trouverIndexSection(sectionActiveId);
+ return index >= 0 && index < toutesSections.size() - 1;
+ }
+
+ private int trouverIndexSection(String sectionId) {
+ for (int i = 0; i < toutesSections.size(); i++) {
+ if (toutesSections.get(i).getId().equals(sectionId)) {
+ return i;
+ }
+ }
+ return -1;
+ }
+
+ // Marquer comme lu
+ public void marquerCommeLu() {
+ if (sectionCourante != null && !sectionCourante.getId().equals("default")) {
+ sectionCourante.setLu(true);
+ // Mettre à jour aussi dans la liste principale
+ toutesSections.stream()
+ .filter(s -> s.getId().equals(sectionCourante.getId()))
+ .findFirst()
+ .ifPresent(s -> s.setLu(true));
+ }
+ }
+
+ // Recherche
+ public List getResultatsRecherche() {
+ if (termeRecherche == null || termeRecherche.trim().isEmpty()) {
+ return new ArrayList<>();
+ }
+
+ String terme = termeRecherche.toLowerCase();
+ return toutesSections.stream()
+ .filter(s -> s.getTitre().toLowerCase().contains(terme) ||
+ s.getDescription().toLowerCase().contains(terme) ||
+ s.getCategorie().toLowerCase().contains(terme))
+ .limit(8)
+ .collect(Collectors.toList());
+ }
+
+ // Getters et Setters
+ public SectionGuide getSectionCourante() { return sectionCourante; }
+ public void setSectionCourante(SectionGuide sectionCourante) { this.sectionCourante = sectionCourante; }
+
+ public String getSectionActiveId() { return sectionActiveId; }
+ public void setSectionActiveId(String sectionActiveId) { this.sectionActiveId = sectionActiveId; }
+
+ public int getSectionActive() { return sectionActive; }
+ public void setSectionActive(int sectionActive) { this.sectionActive = sectionActive; }
+
+ public String getTermeRecherche() { return termeRecherche; }
+ public void setTermeRecherche(String termeRecherche) { this.termeRecherche = termeRecherche; }
+
+ // Classe interne SectionGuide
+ public static class SectionGuide implements Serializable {
+ private String id;
+ private String titre;
+ private String categorie;
+ private String description;
+ private int tempsLecture; // en minutes
+ private boolean lu;
+
+ public SectionGuide() {}
+
+ public SectionGuide(String id, String titre, String categorie, String description, int tempsLecture, boolean lu) {
+ this.id = id;
+ this.titre = titre;
+ this.categorie = categorie;
+ this.description = description;
+ this.tempsLecture = tempsLecture;
+ this.lu = lu;
+ }
+
+ // Getters et Setters
+ public String getId() { return id; }
+ public void setId(String id) { this.id = id; }
+
+ public String getTitre() { return titre; }
+ public void setTitre(String titre) { this.titre = titre; }
+
+ public String getCategorie() { return categorie; }
+ public void setCategorie(String categorie) { this.categorie = categorie; }
+
+ public String getDescription() { return description; }
+ public void setDescription(String description) { this.description = description; }
+
+ public int getTempsLecture() { return tempsLecture; }
+ public void setTempsLecture(int tempsLecture) { this.tempsLecture = tempsLecture; }
+
+ public boolean isLu() { return lu; }
+ public void setLu(boolean lu) { this.lu = lu; }
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/HelloView.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/HelloView.java
new file mode 100644
index 0000000..bceab66
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/HelloView.java
@@ -0,0 +1,48 @@
+package dev.lions.unionflow.client.view;
+
+import jakarta.enterprise.context.RequestScoped;
+import jakarta.inject.Named;
+import java.io.Serializable;
+
+@Named("helloView")
+@RequestScoped
+public class HelloView implements Serializable {
+
+ private static final long serialVersionUID = 1L;
+
+ private String message = "Bienvenue sur UnionFlow avec Quarkus et PrimeFaces!";
+ private String name;
+ private String greeting;
+
+ public void sayHello() {
+ if (name != null && !name.isEmpty()) {
+ greeting = "Bonjour " + name + " ! Bienvenue sur UnionFlow.";
+ } else {
+ greeting = "Veuillez entrer votre nom.";
+ }
+ }
+
+ public String getMessage() {
+ return message;
+ }
+
+ public void setMessage(String message) {
+ this.message = message;
+ }
+
+ public String getName() {
+ return name;
+ }
+
+ public void setName(String name) {
+ this.name = name;
+ }
+
+ public String getGreeting() {
+ return greeting;
+ }
+
+ public void setGreeting(String greeting) {
+ this.greeting = greeting;
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/LoginBean.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/LoginBean.java
new file mode 100644
index 0000000..c510e9c
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/LoginBean.java
@@ -0,0 +1,201 @@
+package dev.lions.unionflow.client.view;
+
+import dev.lions.unionflow.client.dto.auth.LoginRequest;
+import dev.lions.unionflow.client.dto.auth.LoginResponse;
+import dev.lions.unionflow.client.security.JwtTokenManager;
+import dev.lions.unionflow.client.service.AuthenticationService;
+import jakarta.enterprise.context.RequestScoped;
+import jakarta.faces.application.FacesMessage;
+import jakarta.faces.context.FacesContext;
+import jakarta.inject.Inject;
+import jakarta.inject.Named;
+import jakarta.validation.Valid;
+import java.io.Serializable;
+import java.util.logging.Logger;
+
+@Named("loginBean")
+@RequestScoped
+public class LoginBean implements Serializable {
+
+ private static final long serialVersionUID = 1L;
+ private static final Logger LOGGER = Logger.getLogger(LoginBean.class.getName());
+
+ @Inject
+ private UserSession userSession;
+
+ @Inject
+ private JwtTokenManager tokenManager;
+
+ @Inject
+ private AuthenticationService authService;
+
+ private String username;
+ private String password;
+ private String typeCompte;
+ private boolean rememberMe;
+
+ public String login() {
+ try {
+ if (username == null || username.trim().isEmpty() ||
+ password == null || password.trim().isEmpty() ||
+ typeCompte == null || typeCompte.trim().isEmpty()) {
+
+ addErrorMessage("Erreur de validation", "Tous les champs sont requis");
+ return null;
+ }
+
+ LoginRequest loginRequest = new LoginRequest(username, password, typeCompte);
+ loginRequest.setRememberMe(rememberMe);
+
+ LoginResponse response = authService.authenticate(loginRequest);
+
+ // Mettre à jour la session utilisateur
+ userSession.updateFromLoginResponse(response);
+
+ // Gérer les tokens JWT
+ tokenManager.setTokens(response);
+
+ LOGGER.info("Connexion réussie pour: " + username + " (Type: " + typeCompte + ")");
+
+ addSuccessMessage("Connexion réussie", "Bienvenue " + userSession.getCurrentUser().getNomComplet());
+
+ // Redirection selon le type de compte
+ return getRedirectUrlForUserType(response.getUser().getTypeCompte());
+
+ } catch (AuthenticationService.AuthenticationException e) {
+ LOGGER.warning("Échec de l'authentification: " + e.getMessage());
+ addErrorMessage("Erreur de connexion", e.getMessage());
+ return null;
+ } catch (Exception e) {
+ LOGGER.severe("Erreur inattendue lors de la connexion: " + e.getMessage());
+ addErrorMessage("Erreur système", "Une erreur inattendue s'est produite. Veuillez réessayer.");
+ return null;
+ }
+ }
+
+ public String loginDemo(String demoType) {
+ try {
+ String demoUsername;
+ String demoPassword = "admin";
+
+ switch (demoType) {
+ case "SUPER_ADMIN":
+ demoUsername = "superadmin";
+ typeCompte = "SUPER_ADMIN";
+ break;
+ case "ADMIN":
+ demoUsername = "admin";
+ typeCompte = "ADMIN_ENTITE";
+ break;
+ case "MEMBRE":
+ demoUsername = "membre";
+ demoPassword = "membre";
+ typeCompte = "MEMBRE";
+ break;
+ default:
+ addErrorMessage("Erreur", "Type de démo invalide");
+ return null;
+ }
+
+ this.username = demoUsername;
+ this.password = demoPassword;
+
+ return login();
+
+ } catch (Exception e) {
+ LOGGER.severe("Erreur lors de la connexion démo: " + e.getMessage());
+ addErrorMessage("Erreur système", "Impossible de se connecter en mode démo");
+ return null;
+ }
+ }
+
+ public String logout() {
+ try {
+ // Invalider le token côté serveur si possible
+ if (tokenManager.hasValidTokens()) {
+ authService.logout(tokenManager.getAccessToken());
+ }
+
+ // Nettoyer la session locale
+ tokenManager.clearTokens();
+ userSession.clearSession();
+
+ // Invalider la session JSF
+ FacesContext.getCurrentInstance().getExternalContext().invalidateSession();
+
+ LOGGER.info("Déconnexion réussie");
+
+ return "/pages/public/login?faces-redirect=true";
+
+ } catch (Exception e) {
+ LOGGER.warning("Erreur lors de la déconnexion: " + e.getMessage());
+
+ // Même en cas d'erreur, invalider la session locale
+ tokenManager.clearTokens();
+ userSession.clearSession();
+ FacesContext.getCurrentInstance().getExternalContext().invalidateSession();
+
+ return "/pages/public/login?faces-redirect=true";
+ }
+ }
+
+ private String getRedirectUrlForUserType(String typeCompte) {
+ if (typeCompte == null) {
+ return "/pages/secure/dashboard?faces-redirect=true";
+ }
+
+ switch (typeCompte) {
+ case "SUPER_ADMIN":
+ return "/pages/super-admin/dashboard?faces-redirect=true";
+ case "ADMIN_ENTITE":
+ return "/pages/admin/dashboard?faces-redirect=true";
+ case "MEMBRE":
+ return "/pages/membre/dashboard?faces-redirect=true";
+ default:
+ return "/pages/secure/dashboard?faces-redirect=true";
+ }
+ }
+
+ private void addErrorMessage(String summary, String detail) {
+ FacesContext.getCurrentInstance().addMessage(null,
+ new FacesMessage(FacesMessage.SEVERITY_ERROR, summary, detail));
+ }
+
+ private void addSuccessMessage(String summary, String detail) {
+ FacesContext.getCurrentInstance().addMessage(null,
+ new FacesMessage(FacesMessage.SEVERITY_INFO, summary, detail));
+ }
+
+ // Getters et Setters
+ public String getUsername() {
+ return username;
+ }
+
+ public void setUsername(String username) {
+ this.username = username;
+ }
+
+ public String getPassword() {
+ return password;
+ }
+
+ public void setPassword(String password) {
+ this.password = password;
+ }
+
+ public String getTypeCompte() {
+ return typeCompte;
+ }
+
+ public void setTypeCompte(String typeCompte) {
+ this.typeCompte = typeCompte;
+ }
+
+ public boolean isRememberMe() {
+ return rememberMe;
+ }
+
+ public void setRememberMe(boolean rememberMe) {
+ this.rememberMe = rememberMe;
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/MembreCotisationBean.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/MembreCotisationBean.java
new file mode 100644
index 0000000..4706a01
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/MembreCotisationBean.java
@@ -0,0 +1,441 @@
+package dev.lions.unionflow.client.view;
+
+import jakarta.enterprise.context.SessionScoped;
+import jakarta.inject.Named;
+import jakarta.annotation.PostConstruct;
+import java.io.Serializable;
+import java.math.BigDecimal;
+import java.time.LocalDate;
+import java.util.ArrayList;
+import java.util.List;
+
+@Named("membreCotisationBean")
+@SessionScoped
+public class MembreCotisationBean implements Serializable {
+
+ private static final long serialVersionUID = 1L;
+
+ // Propriétés de base
+ private String numeroMembre;
+ private String statutCotisations;
+ private String derniereMAJ;
+ private boolean peutPayer;
+
+ // Statistiques
+ private int cotisationsPayees;
+ private int cotisationsEnAttente;
+ private BigDecimal montantDu;
+ private BigDecimal totalVerse;
+ private int progressionAnnuelle;
+
+ // Filtres
+ private String anneeFilter = "2024";
+ private String statutFilter = "";
+ private String typeFilter = "";
+
+ // Paiement
+ private Object cotisationSelectionnee;
+ private String modePaiementChoisi = "WAVE";
+ private String numeroWave;
+ private String commentairePaiement;
+ private BigDecimal montantAPayer = BigDecimal.ZERO;
+ private String banqueAssociation = "Banque Atlantique";
+ private String ibanAssociation = "SN12 1234 5678 9012 3456 7890 12";
+
+ // Prélèvement automatique
+ private String numeroWaveAuto;
+ private int jourPrelevement = 5;
+ private boolean notificationSMS = true;
+ private String cotisationMensuelle = "5,000 FCFA";
+
+ // Listes
+ private List cotisations = new ArrayList<>();
+ private List prochainesEcheances = new ArrayList<>();
+ private List cotisationsImpayees = new ArrayList<>();
+
+ // Totaux périodes
+ private BigDecimal totalPayePeriode = BigDecimal.ZERO;
+ private BigDecimal totalEnAttentePeriode = BigDecimal.ZERO;
+ private BigDecimal totalEnRetardPeriode = BigDecimal.ZERO;
+ private int tauxConformite = 85;
+
+ // État
+ private String statutMembre = "Actif";
+ private String typeMembre = "Membre Actif";
+ private String statutSeverity = "success";
+ private int scorePonctualite = 85;
+ private String commentairePonctualite = "Excellent membre, toujours à jour";
+
+ @PostConstruct
+ public void init() {
+ this.numeroMembre = "M240001";
+ this.statutCotisations = "À jour";
+ this.derniereMAJ = "15/12/2024";
+ this.peutPayer = true;
+ this.cotisationsPayees = 10;
+ this.cotisationsEnAttente = 2;
+ this.montantDu = new BigDecimal(10000);
+ this.totalVerse = new BigDecimal(50000);
+ this.progressionAnnuelle = 83;
+
+ initializeCotisations();
+ initializeEcheances();
+ }
+
+ private void initializeCotisations() {
+ // Simulation de données
+ for (int i = 1; i <= 12; i++) {
+ Cotisation cotisation = new Cotisation();
+ cotisation.setReference("COT2024" + String.format("%03d", i));
+ cotisation.setLibelle("Cotisation " + getMonthName(i) + " 2024");
+ cotisation.setPeriode(getMonthName(i) + " 2024");
+ cotisation.setType("MENSUELLE");
+ cotisation.setMontant(new BigDecimal(5000));
+ cotisation.setStatut(i <= 10 ? "PAYE" : "EN_ATTENTE");
+ cotisation.setDateEcheance(LocalDate.of(2024, i, 15));
+ if (i <= 10) {
+ cotisation.setDatePaiement(LocalDate.of(2024, i, i <= 5 ? 10 : 20));
+ cotisation.setModePaiement("Wave Money");
+ }
+ cotisations.add(cotisation);
+
+ if (i > 10) {
+ cotisationsImpayees.add(cotisation);
+ }
+ }
+ }
+
+ private void initializeEcheances() {
+ Echeance echeance1 = new Echeance();
+ echeance1.setLibelle("Cotisation Novembre 2024");
+ echeance1.setPeriode("Novembre 2024");
+ echeance1.setMontant("5,000 FCFA");
+ echeance1.setDateEcheance("15/11/2024");
+ echeance1.setUrgence("En retard");
+ echeance1.setCouleurUrgence("border-red-500");
+ prochainesEcheances.add(echeance1);
+
+ Echeance echeance2 = new Echeance();
+ echeance2.setLibelle("Cotisation Décembre 2024");
+ echeance2.setPeriode("Décembre 2024");
+ echeance2.setMontant("5,000 FCFA");
+ echeance2.setDateEcheance("15/12/2024");
+ echeance2.setUrgence("Bientôt");
+ echeance2.setCouleurUrgence("border-orange-500");
+ prochainesEcheances.add(echeance2);
+ }
+
+ private String getMonthName(int month) {
+ String[] months = {"Janvier", "Février", "Mars", "Avril", "Mai", "Juin",
+ "Juillet", "Août", "Septembre", "Octobre", "Novembre", "Décembre"};
+ return months[month - 1];
+ }
+
+ // Actions
+ public String voirHistoriqueComplet() {
+ return "/pages/membre/historique-cotisations?faces-redirect=true";
+ }
+
+ public void telechargerRecus() {
+ // Logique de téléchargement des reçus
+ }
+
+ public void payerCotisation(Object cotisation) {
+ // Logique de paiement d'une cotisation
+ }
+
+ public void actualiser() {
+ // Actualiser les données
+ init();
+ }
+
+ public String confirmerPaiement() {
+ // Logique de confirmation de paiement
+ return null;
+ }
+
+ public void paiementWave() {
+ // Logique de paiement Wave Money
+ }
+
+ public void genererAttestation() {
+ // Logique de génération d'attestation
+ }
+
+ public void demanderRecu() {
+ // Logique de demande de reçu
+ }
+
+ public void activerPrelevementAuto() {
+ // Logique d'activation du prélèvement automatique
+ }
+
+ public void telechargerRecu(Object cotisation) {
+ // Logique de téléchargement de reçu
+ }
+
+ public void voirDetails(Object cotisation) {
+ // Logique d'affichage des détails
+ }
+
+ // Getters et Setters
+ public String getNumeroMembre() { return numeroMembre; }
+ public void setNumeroMembre(String numeroMembre) { this.numeroMembre = numeroMembre; }
+
+ public String getStatutCotisations() { return statutCotisations; }
+ public void setStatutCotisations(String statutCotisations) { this.statutCotisations = statutCotisations; }
+
+ public String getDerniereMAJ() { return derniereMAJ; }
+ public void setDerniereMAJ(String derniereMAJ) { this.derniereMAJ = derniereMAJ; }
+
+ public boolean isPeutPayer() { return peutPayer; }
+ public void setPeutPayer(boolean peutPayer) { this.peutPayer = peutPayer; }
+
+ public int getCotisationsPayees() { return cotisationsPayees; }
+ public void setCotisationsPayees(int cotisationsPayees) { this.cotisationsPayees = cotisationsPayees; }
+
+ public int getCotisationsEnAttente() { return cotisationsEnAttente; }
+ public void setCotisationsEnAttente(int cotisationsEnAttente) { this.cotisationsEnAttente = cotisationsEnAttente; }
+
+ public BigDecimal getMontantDu() { return montantDu; }
+ public void setMontantDu(BigDecimal montantDu) { this.montantDu = montantDu; }
+
+ public BigDecimal getTotalVerse() { return totalVerse; }
+ public void setTotalVerse(BigDecimal totalVerse) { this.totalVerse = totalVerse; }
+
+ public int getProgressionAnnuelle() { return progressionAnnuelle; }
+ public void setProgressionAnnuelle(int progressionAnnuelle) { this.progressionAnnuelle = progressionAnnuelle; }
+
+ public String getAnneeFilter() { return anneeFilter; }
+ public void setAnneeFilter(String anneeFilter) { this.anneeFilter = anneeFilter; }
+
+ public String getStatutFilter() { return statutFilter; }
+ public void setStatutFilter(String statutFilter) { this.statutFilter = statutFilter; }
+
+ public String getTypeFilter() { return typeFilter; }
+ public void setTypeFilter(String typeFilter) { this.typeFilter = typeFilter; }
+
+ public List getCotisations() { return cotisations; }
+ public void setCotisations(List cotisations) { this.cotisations = cotisations; }
+
+ public List getProchainesEcheances() { return prochainesEcheances; }
+ public void setProchainesEcheances(List prochainesEcheances) { this.prochainesEcheances = prochainesEcheances; }
+
+ public Object getCotisationSelectionnee() { return cotisationSelectionnee; }
+ public void setCotisationSelectionnee(Object cotisationSelectionnee) { this.cotisationSelectionnee = cotisationSelectionnee; }
+
+ public List getCotisationsImpayees() { return cotisationsImpayees; }
+ public void setCotisationsImpayees(List cotisationsImpayees) { this.cotisationsImpayees = cotisationsImpayees; }
+
+ public String getModePaiementChoisi() { return modePaiementChoisi; }
+ public void setModePaiementChoisi(String modePaiementChoisi) { this.modePaiementChoisi = modePaiementChoisi; }
+
+ public String getNumeroWave() { return numeroWave; }
+ public void setNumeroWave(String numeroWave) { this.numeroWave = numeroWave; }
+
+ public String getCommentairePaiement() { return commentairePaiement; }
+ public void setCommentairePaiement(String commentairePaiement) { this.commentairePaiement = commentairePaiement; }
+
+ public BigDecimal getMontantAPayer() { return montantAPayer; }
+ public void setMontantAPayer(BigDecimal montantAPayer) { this.montantAPayer = montantAPayer; }
+
+ public String getBanqueAssociation() { return banqueAssociation; }
+ public void setBanqueAssociation(String banqueAssociation) { this.banqueAssociation = banqueAssociation; }
+
+ public String getIbanAssociation() { return ibanAssociation; }
+ public void setIbanAssociation(String ibanAssociation) { this.ibanAssociation = ibanAssociation; }
+
+ public String getNumeroWaveAuto() { return numeroWaveAuto; }
+ public void setNumeroWaveAuto(String numeroWaveAuto) { this.numeroWaveAuto = numeroWaveAuto; }
+
+ public int getJourPrelevement() { return jourPrelevement; }
+ public void setJourPrelevement(int jourPrelevement) { this.jourPrelevement = jourPrelevement; }
+
+ public boolean isNotificationSMS() { return notificationSMS; }
+ public void setNotificationSMS(boolean notificationSMS) { this.notificationSMS = notificationSMS; }
+
+ public String getCotisationMensuelle() { return cotisationMensuelle; }
+ public void setCotisationMensuelle(String cotisationMensuelle) { this.cotisationMensuelle = cotisationMensuelle; }
+
+ public BigDecimal getTotalPayePeriode() { return totalPayePeriode; }
+ public void setTotalPayePeriode(BigDecimal totalPayePeriode) { this.totalPayePeriode = totalPayePeriode; }
+
+ public BigDecimal getTotalEnAttentePeriode() { return totalEnAttentePeriode; }
+ public void setTotalEnAttentePeriode(BigDecimal totalEnAttentePeriode) { this.totalEnAttentePeriode = totalEnAttentePeriode; }
+
+ public BigDecimal getTotalEnRetardPeriode() { return totalEnRetardPeriode; }
+ public void setTotalEnRetardPeriode(BigDecimal totalEnRetardPeriode) { this.totalEnRetardPeriode = totalEnRetardPeriode; }
+
+ public int getTauxConformite() { return tauxConformite; }
+ public void setTauxConformite(int tauxConformite) { this.tauxConformite = tauxConformite; }
+
+ public String getStatutMembre() { return statutMembre; }
+ public void setStatutMembre(String statutMembre) { this.statutMembre = statutMembre; }
+
+ public String getTypeMembre() { return typeMembre; }
+ public void setTypeMembre(String typeMembre) { this.typeMembre = typeMembre; }
+
+ public String getStatutSeverity() { return statutSeverity; }
+ public void setStatutSeverity(String statutSeverity) { this.statutSeverity = statutSeverity; }
+
+ public int getScorePonctualite() { return scorePonctualite; }
+ public void setScorePonctualite(int scorePonctualite) { this.scorePonctualite = scorePonctualite; }
+
+ public String getCommentairePonctualite() { return commentairePonctualite; }
+ public void setCommentairePonctualite(String commentairePonctualite) { this.commentairePonctualite = commentairePonctualite; }
+
+ public boolean isPeutPayerWave() { return true; }
+
+ // Méthodes pour les charts
+ public Object getHistoriquePaiementsChart() {
+ // Retourner un objet chart model vide pour l'instant
+ return null;
+ }
+
+ // Classes internes pour les données
+ public static class Cotisation {
+ private String reference;
+ private String libelle;
+ private String periode;
+ private String type;
+ private BigDecimal montant;
+ private String statut;
+ private LocalDate dateEcheance;
+ private LocalDate datePaiement;
+ private String modePaiement;
+
+ // Getters et setters
+ public String getReference() { return reference; }
+ public void setReference(String reference) { this.reference = reference; }
+
+ public String getLibelle() { return libelle; }
+ public void setLibelle(String libelle) { this.libelle = libelle; }
+
+ public String getPeriode() { return periode; }
+ public void setPeriode(String periode) { this.periode = periode; }
+
+ public String getType() { return type; }
+ public void setType(String type) { this.type = type; }
+
+ public BigDecimal getMontant() { return montant; }
+ public void setMontant(BigDecimal montant) { this.montant = montant; }
+
+ public String getStatut() { return statut; }
+ public void setStatut(String statut) { this.statut = statut; }
+
+ public LocalDate getDateEcheance() { return dateEcheance; }
+ public void setDateEcheance(LocalDate dateEcheance) { this.dateEcheance = dateEcheance; }
+
+ public LocalDate getDatePaiement() { return datePaiement; }
+ public void setDatePaiement(LocalDate datePaiement) { this.datePaiement = datePaiement; }
+
+ public String getModePaiement() { return modePaiement; }
+ public void setModePaiement(String modePaiement) { this.modePaiement = modePaiement; }
+
+ // Propriétés dérivées pour l'affichage
+ public String getTypeSeverity() {
+ return switch (type) {
+ case "MENSUELLE" -> "info";
+ case "SPECIALE" -> "warning";
+ case "ADHESION" -> "success";
+ default -> "secondary";
+ };
+ }
+
+ public String getTypeIcon() {
+ return switch (type) {
+ case "MENSUELLE" -> "pi-calendar";
+ case "SPECIALE" -> "pi-star";
+ case "ADHESION" -> "pi-user-plus";
+ default -> "pi-circle";
+ };
+ }
+
+ public String getStatutSeverity() {
+ return switch (statut) {
+ case "PAYE" -> "success";
+ case "EN_ATTENTE" -> "warning";
+ case "EN_RETARD" -> "danger";
+ default -> "secondary";
+ };
+ }
+
+ public String getStatutIcon() {
+ return switch (statut) {
+ case "PAYE" -> "pi-check";
+ case "EN_ATTENTE" -> "pi-clock";
+ case "EN_RETARD" -> "pi-exclamation-triangle";
+ default -> "pi-circle";
+ };
+ }
+
+ public String getRetardColor() {
+ return switch (statut) {
+ case "EN_RETARD" -> "text-red-500";
+ case "EN_ATTENTE" -> "text-orange-500";
+ default -> "text-600";
+ };
+ }
+
+ public String getStatutEcheance() {
+ return switch (statut) {
+ case "EN_RETARD" -> "En retard";
+ case "EN_ATTENTE" -> "À venir";
+ default -> "Payée";
+ };
+ }
+
+ public String getModePaiementIcon() {
+ return switch (modePaiement != null ? modePaiement : "") {
+ case "Wave Money" -> "pi-mobile";
+ case "Virement" -> "pi-building";
+ case "Espèces" -> "pi-money-bill";
+ default -> "pi-circle";
+ };
+ }
+
+ public String getCouleurMontant() {
+ return "text-900";
+ }
+ }
+
+ public static class Echeance {
+ private String libelle;
+ private String periode;
+ private String montant;
+ private String dateEcheance;
+ private String urgence;
+ private String couleurUrgence;
+
+ // Getters et setters
+ public String getLibelle() { return libelle; }
+ public void setLibelle(String libelle) { this.libelle = libelle; }
+
+ public String getPeriode() { return periode; }
+ public void setPeriode(String periode) { this.periode = periode; }
+
+ public String getMontant() { return montant; }
+ public void setMontant(String montant) { this.montant = montant; }
+
+ public String getDateEcheance() { return dateEcheance; }
+ public void setDateEcheance(String dateEcheance) { this.dateEcheance = dateEcheance; }
+
+ public String getUrgence() { return urgence; }
+ public void setUrgence(String urgence) { this.urgence = urgence; }
+
+ public String getCouleurUrgence() { return couleurUrgence; }
+ public void setCouleurUrgence(String couleurUrgence) { this.couleurUrgence = couleurUrgence; }
+
+ public String getUrgenceSeverity() {
+ return switch (urgence) {
+ case "En retard" -> "danger";
+ case "Bientôt" -> "warning";
+ default -> "info";
+ };
+ }
+
+ public String getCouleurMontant() {
+ return "text-900";
+ }
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/MembreDashboardBean.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/MembreDashboardBean.java
new file mode 100644
index 0000000..65d9697
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/MembreDashboardBean.java
@@ -0,0 +1,410 @@
+package dev.lions.unionflow.client.view;
+
+import jakarta.enterprise.context.SessionScoped;
+import jakarta.inject.Named;
+import jakarta.annotation.PostConstruct;
+import java.io.Serializable;
+import java.time.LocalDate;
+import java.util.ArrayList;
+import java.util.List;
+
+@Named("membreDashboardBean")
+@SessionScoped
+public class MembreDashboardBean implements Serializable {
+
+ private static final long serialVersionUID = 1L;
+
+ // Membre actuel
+ private Membre membre;
+
+ // Statistiques
+ private String statutCotisations;
+ private int evenementsInscrits;
+ private int aidesRecues;
+ private int messagesNonLus;
+
+ // Progression
+ private int cotisationsPayees;
+ private int cotisationsTotales;
+ private int progressionCotisations;
+ private int tauxParticipation;
+ private int evenementsAssistes;
+ private String anciennete;
+ private String dateAdhesionFormatee;
+
+ // Listes
+ private List alertes = new ArrayList<>();
+ private List prochainsEvenements = new ArrayList<>();
+ private List rappels = new ArrayList<>();
+ private List activiteRecente = new ArrayList<>();
+
+ // État
+ private boolean peutPayerCotisations;
+
+ @PostConstruct
+ public void init() {
+ initializeMembre();
+ initializeStatistiques();
+ initializeAlertes();
+ initializeEvenements();
+ initializeRappels();
+ initializeActivite();
+ }
+
+ private void initializeMembre() {
+ membre = new Membre();
+ membre.setPrenom("Jean");
+ membre.setNom("Dupont");
+ membre.setNumeroMembre("M240001");
+ membre.setTypeMembre("Membre Actif");
+ membre.setDateAdhesion("15/06/2020");
+ membre.setPhotoUrl(null); // Pas de photo par défaut
+ }
+
+ private void initializeStatistiques() {
+ this.statutCotisations = "À jour";
+ this.evenementsInscrits = 3;
+ this.aidesRecues = 2;
+ this.messagesNonLus = 5;
+ this.cotisationsPayees = 10;
+ this.cotisationsTotales = 12;
+ this.progressionCotisations = 83;
+ this.tauxParticipation = 75;
+ this.evenementsAssistes = 15;
+ this.anciennete = "4 ans";
+ this.dateAdhesionFormatee = "15 juin 2020";
+ this.peutPayerCotisations = true;
+ }
+
+ private void initializeAlertes() {
+ Alerte alerte1 = new Alerte();
+ alerte1.setTitre("Cotisation de décembre");
+ alerte1.setMessage("Votre cotisation mensuelle de décembre est due le 15/12/2024");
+ alerte1.setDateRelative("Il y a 2 jours");
+ alerte1.setIcone("pi-dollar");
+ alerte1.setCouleurIcone("text-orange-500");
+ alerte1.setCouleurFond("rgba(255, 193, 7, 0.1)");
+ alerte1.setCouleurBordure("border-orange-500");
+ alertes.add(alerte1);
+
+ Alerte alerte2 = new Alerte();
+ alerte2.setTitre("Nouvel événement");
+ alerte2.setMessage("Assemblée générale prévue le 28 décembre 2024");
+ alerte2.setDateRelative("Hier");
+ alerte2.setIcone("pi-calendar");
+ alerte2.setCouleurIcone("text-blue-500");
+ alerte2.setCouleurFond("rgba(13, 110, 253, 0.1)");
+ alerte2.setCouleurBordure("border-blue-500");
+ alertes.add(alerte2);
+ }
+
+ private void initializeEvenements() {
+ Evenement event1 = new Evenement();
+ event1.setTitre("Assemblée Générale Ordinaire");
+ event1.setDateComplete("Samedi 28 décembre 2024 - 09h00");
+ event1.setLieu("Siège de l'association");
+ event1.setPrixFormate("Gratuit");
+ event1.setNombreParticipants("45 inscrits");
+ event1.setStatutInscription("Inscrit");
+ event1.setSeverityInscription("success");
+ event1.setIconeType("pi-users");
+ event1.setCouleurCategorie("bg-blue-500");
+ event1.setCouleurBordure("border-blue-500");
+ event1.setPeutAnnuler(true);
+ prochainsEvenements.add(event1);
+
+ Evenement event2 = new Evenement();
+ event2.setTitre("Formation premiers secours");
+ event2.setDateComplete("Dimanche 15 janvier 2025 - 14h00");
+ event2.setLieu("Centre de formation");
+ event2.setPrixFormate("2,500 FCFA");
+ event2.setNombreParticipants("12 inscrits");
+ event2.setStatutInscription("En attente");
+ event2.setSeverityInscription("warning");
+ event2.setIconeType("pi-heart");
+ event2.setCouleurCategorie("bg-red-500");
+ event2.setCouleurBordure("border-red-500");
+ event2.setPeutAnnuler(false);
+ prochainsEvenements.add(event2);
+ }
+
+ private void initializeRappels() {
+ Rappel rappel1 = new Rappel();
+ rappel1.setTitre("Cotisation décembre");
+ rappel1.setEcheance("Dans 3 jours");
+ rappel1.setIcone("pi-dollar");
+ rappel1.setCouleurIcone("text-orange-500");
+ rappel1.setCouleurFond("surface-100");
+ rappels.add(rappel1);
+
+ Rappel rappel2 = new Rappel();
+ rappel2.setTitre("Renouvellement adhésion");
+ rappel2.setEcheance("Dans 2 mois");
+ rappel2.setIcone("pi-id-card");
+ rappel2.setCouleurIcone("text-blue-500");
+ rappel2.setCouleurFond("surface-100");
+ rappels.add(rappel2);
+ }
+
+ private void initializeActivite() {
+ Activite activite1 = new Activite();
+ activite1.setTitre("Cotisation payée");
+ activite1.setDescription("Cotisation de novembre 2024 - 5,000 FCFA");
+ activite1.setDateRelative("Il y a 5 jours");
+ activite1.setIcone("pi-check");
+ activite1.setCouleurCategorie("bg-green-500");
+ activiteRecente.add(activite1);
+
+ Activite activite2 = new Activite();
+ activite2.setTitre("Participation événement");
+ activite2.setDescription("Sortie culturelle au musée");
+ activite2.setDateRelative("Il y a 1 semaine");
+ activite2.setIcone("pi-calendar");
+ activite2.setCouleurCategorie("bg-blue-500");
+ activiteRecente.add(activite2);
+
+ Activite activite3 = new Activite();
+ activite3.setTitre("Inscription événement");
+ activite3.setDescription("Assemblée générale ordinaire");
+ activite3.setDateRelative("Il y a 2 semaines");
+ activite3.setIcone("pi-user-plus");
+ activite3.setCouleurCategorie("bg-purple-500");
+ activiteRecente.add(activite3);
+ }
+
+ // Actions
+ public void marquerLue(Alerte alerte) {
+ alertes.remove(alerte);
+ }
+
+ public String voirEvenement(Evenement evenement) {
+ return "/pages/membre/evenement?id=" + evenement.getTitre() + "&faces-redirect=true";
+ }
+
+ public void annulerInscription(Evenement evenement) {
+ evenement.setStatutInscription("Annulé");
+ evenement.setSeverityInscription("danger");
+ evenement.setPeutAnnuler(false);
+ }
+
+ public String payerCotisations() {
+ return "/pages/membre/cotisations?faces-redirect=true";
+ }
+
+ // Getters et Setters
+ public Membre getMembre() { return membre; }
+ public void setMembre(Membre membre) { this.membre = membre; }
+
+ public String getStatutCotisations() { return statutCotisations; }
+ public void setStatutCotisations(String statutCotisations) { this.statutCotisations = statutCotisations; }
+
+ public int getEvenementsInscrits() { return evenementsInscrits; }
+ public void setEvenementsInscrits(int evenementsInscrits) { this.evenementsInscrits = evenementsInscrits; }
+
+ public int getAidesRecues() { return aidesRecues; }
+ public void setAidesRecues(int aidesRecues) { this.aidesRecues = aidesRecues; }
+
+ public int getMessagesNonLus() { return messagesNonLus; }
+ public void setMessagesNonLus(int messagesNonLus) { this.messagesNonLus = messagesNonLus; }
+
+ public int getCotisationsPayees() { return cotisationsPayees; }
+ public void setCotisationsPayees(int cotisationsPayees) { this.cotisationsPayees = cotisationsPayees; }
+
+ public int getCotisationsTotales() { return cotisationsTotales; }
+ public void setCotisationsTotales(int cotisationsTotales) { this.cotisationsTotales = cotisationsTotales; }
+
+ public int getProgressionCotisations() { return progressionCotisations; }
+ public void setProgressionCotisations(int progressionCotisations) { this.progressionCotisations = progressionCotisations; }
+
+ public int getTauxParticipation() { return tauxParticipation; }
+ public void setTauxParticipation(int tauxParticipation) { this.tauxParticipation = tauxParticipation; }
+
+ public int getEvenementsAssistes() { return evenementsAssistes; }
+ public void setEvenementsAssistes(int evenementsAssistes) { this.evenementsAssistes = evenementsAssistes; }
+
+ public String getAnciennete() { return anciennete; }
+ public void setAnciennete(String anciennete) { this.anciennete = anciennete; }
+
+ public String getDateAdhesionFormatee() { return dateAdhesionFormatee; }
+ public void setDateAdhesionFormatee(String dateAdhesionFormatee) { this.dateAdhesionFormatee = dateAdhesionFormatee; }
+
+ public List getAlertes() { return alertes; }
+ public void setAlertes(List alertes) { this.alertes = alertes; }
+
+ public List getProchainsEvenements() { return prochainsEvenements; }
+ public void setProchainsEvenements(List prochainsEvenements) { this.prochainsEvenements = prochainsEvenements; }
+
+ public List getRappels() { return rappels; }
+ public void setRappels(List rappels) { this.rappels = rappels; }
+
+ public List getActiviteRecente() { return activiteRecente; }
+ public void setActiviteRecente(List activiteRecente) { this.activiteRecente = activiteRecente; }
+
+ public boolean isPeutPayerCotisations() { return peutPayerCotisations; }
+ public void setPeutPayerCotisations(boolean peutPayerCotisations) { this.peutPayerCotisations = peutPayerCotisations; }
+
+ // Classes internes
+ public static class Membre {
+ private String prenom;
+ private String nom;
+ private String numeroMembre;
+ private String typeMembre;
+ private String dateAdhesion;
+ private String photoUrl;
+
+ public String getPrenom() { return prenom; }
+ public void setPrenom(String prenom) { this.prenom = prenom; }
+
+ public String getNom() { return nom; }
+ public void setNom(String nom) { this.nom = nom; }
+
+ public String getNumeroMembre() { return numeroMembre; }
+ public void setNumeroMembre(String numeroMembre) { this.numeroMembre = numeroMembre; }
+
+ public String getTypeMembre() { return typeMembre; }
+ public void setTypeMembre(String typeMembre) { this.typeMembre = typeMembre; }
+
+ public String getDateAdhesion() { return dateAdhesion; }
+ public void setDateAdhesion(String dateAdhesion) { this.dateAdhesion = dateAdhesion; }
+
+ public String getPhotoUrl() { return photoUrl; }
+ public void setPhotoUrl(String photoUrl) { this.photoUrl = photoUrl; }
+
+ public String getInitiales() {
+ return (prenom != null ? prenom.substring(0, 1) : "") +
+ (nom != null ? nom.substring(0, 1) : "");
+ }
+ }
+
+ public static class Alerte {
+ private String titre;
+ private String message;
+ private String dateRelative;
+ private String icone;
+ private String couleurIcone;
+ private String couleurFond;
+ private String couleurBordure;
+
+ // Getters et setters
+ public String getTitre() { return titre; }
+ public void setTitre(String titre) { this.titre = titre; }
+
+ public String getMessage() { return message; }
+ public void setMessage(String message) { this.message = message; }
+
+ public String getDateRelative() { return dateRelative; }
+ public void setDateRelative(String dateRelative) { this.dateRelative = dateRelative; }
+
+ public String getIcone() { return icone; }
+ public void setIcone(String icone) { this.icone = icone; }
+
+ public String getCouleurIcone() { return couleurIcone; }
+ public void setCouleurIcone(String couleurIcone) { this.couleurIcone = couleurIcone; }
+
+ public String getCouleurFond() { return couleurFond; }
+ public void setCouleurFond(String couleurFond) { this.couleurFond = couleurFond; }
+
+ public String getCouleurBordure() { return couleurBordure; }
+ public void setCouleurBordure(String couleurBordure) { this.couleurBordure = couleurBordure; }
+ }
+
+ public static class Evenement {
+ private String titre;
+ private String dateComplete;
+ private String lieu;
+ private String prixFormate;
+ private String nombreParticipants;
+ private String statutInscription;
+ private String severityInscription;
+ private String iconeType;
+ private String couleurCategorie;
+ private String couleurBordure;
+ private boolean peutAnnuler;
+
+ // Getters et setters
+ public String getTitre() { return titre; }
+ public void setTitre(String titre) { this.titre = titre; }
+
+ public String getDateComplete() { return dateComplete; }
+ public void setDateComplete(String dateComplete) { this.dateComplete = dateComplete; }
+
+ public String getLieu() { return lieu; }
+ public void setLieu(String lieu) { this.lieu = lieu; }
+
+ public String getPrixFormate() { return prixFormate; }
+ public void setPrixFormate(String prixFormate) { this.prixFormate = prixFormate; }
+
+ public String getNombreParticipants() { return nombreParticipants; }
+ public void setNombreParticipants(String nombreParticipants) { this.nombreParticipants = nombreParticipants; }
+
+ public String getStatutInscription() { return statutInscription; }
+ public void setStatutInscription(String statutInscription) { this.statutInscription = statutInscription; }
+
+ public String getSeverityInscription() { return severityInscription; }
+ public void setSeverityInscription(String severityInscription) { this.severityInscription = severityInscription; }
+
+ public String getIconeType() { return iconeType; }
+ public void setIconeType(String iconeType) { this.iconeType = iconeType; }
+
+ public String getCouleurCategorie() { return couleurCategorie; }
+ public void setCouleurCategorie(String couleurCategorie) { this.couleurCategorie = couleurCategorie; }
+
+ public String getCouleurBordure() { return couleurBordure; }
+ public void setCouleurBordure(String couleurBordure) { this.couleurBordure = couleurBordure; }
+
+ public boolean isPeutAnnuler() { return peutAnnuler; }
+ public void setPeutAnnuler(boolean peutAnnuler) { this.peutAnnuler = peutAnnuler; }
+
+ public String getCouleurPrix() {
+ return prixFormate.equals("Gratuit") ? "text-green-500" : "text-blue-500";
+ }
+ }
+
+ public static class Rappel {
+ private String titre;
+ private String echeance;
+ private String icone;
+ private String couleurIcone;
+ private String couleurFond;
+
+ // Getters et setters
+ public String getTitre() { return titre; }
+ public void setTitre(String titre) { this.titre = titre; }
+
+ public String getEcheance() { return echeance; }
+ public void setEcheance(String echeance) { this.echeance = echeance; }
+
+ public String getIcone() { return icone; }
+ public void setIcone(String icone) { this.icone = icone; }
+
+ public String getCouleurIcone() { return couleurIcone; }
+ public void setCouleurIcone(String couleurIcone) { this.couleurIcone = couleurIcone; }
+
+ public String getCouleurFond() { return couleurFond; }
+ public void setCouleurFond(String couleurFond) { this.couleurFond = couleurFond; }
+ }
+
+ public static class Activite {
+ private String titre;
+ private String description;
+ private String dateRelative;
+ private String icone;
+ private String couleurCategorie;
+
+ // Getters et setters
+ public String getTitre() { return titre; }
+ public void setTitre(String titre) { this.titre = titre; }
+
+ public String getDescription() { return description; }
+ public void setDescription(String description) { this.description = description; }
+
+ public String getDateRelative() { return dateRelative; }
+ public void setDateRelative(String dateRelative) { this.dateRelative = dateRelative; }
+
+ public String getIcone() { return icone; }
+ public void setIcone(String icone) { this.icone = icone; }
+
+ public String getCouleurCategorie() { return couleurCategorie; }
+ public void setCouleurCategorie(String couleurCategorie) { this.couleurCategorie = couleurCategorie; }
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/MembreInscriptionBean.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/MembreInscriptionBean.java
new file mode 100644
index 0000000..220f2d6
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/MembreInscriptionBean.java
@@ -0,0 +1,454 @@
+package dev.lions.unionflow.client.view;
+
+import dev.lions.unionflow.client.dto.MembreDTO;
+import dev.lions.unionflow.client.dto.AssociationDTO;
+import dev.lions.unionflow.client.service.MembreService;
+import dev.lions.unionflow.client.service.AssociationService;
+import dev.lions.unionflow.client.service.ValidationService;
+import dev.lions.unionflow.client.view.SouscriptionBean;
+import jakarta.enterprise.context.RequestScoped;
+import jakarta.inject.Named;
+import jakarta.inject.Inject;
+import jakarta.annotation.PostConstruct;
+import jakarta.faces.application.FacesMessage;
+import jakarta.faces.context.FacesContext;
+import org.eclipse.microprofile.rest.client.inject.RestClient;
+import java.io.Serializable;
+import java.time.LocalDate;
+import java.time.LocalDateTime;
+import java.util.ArrayList;
+import java.util.List;
+import java.util.UUID;
+
+@Named("membreInscriptionBean")
+@RequestScoped
+public class MembreInscriptionBean implements Serializable {
+
+ private static final long serialVersionUID = 1L;
+
+ @Inject
+ @RestClient
+ MembreService membreService;
+
+ @Inject
+ @RestClient
+ AssociationService associationService;
+
+ @Inject
+ ValidationService validationService;
+
+ @Inject
+ SouscriptionBean souscriptionBean;
+
+ // Propriétés système
+ private String numeroGenere;
+
+ // Informations personnelles
+ private String prenom;
+ private String nom;
+ private String email;
+ private String telephone;
+ private String telephoneMobile;
+ private String adresse;
+ private String ville;
+ private String codePostal;
+ private String pays = "Sénégal";
+ private LocalDate dateNaissance;
+ private String lieuNaissance;
+ private String nationalite = "Sénégalaise";
+ private String sexe;
+ private String situationMatrimoniale;
+ private String profession;
+ private String employeur;
+
+ // Informations d'urgence
+ private String contactUrgenceNom;
+ private String contactUrgenceTelephone;
+ private String contactUrgenceLien;
+
+ // Informations bancaires
+ private String numeroBanque;
+ private String nomBanque;
+ private String ribIban;
+
+ // Informations adhésion
+ private String typeAdhesion;
+ private String numeroParrain;
+ private String nomParrain;
+ private String motifAdhesion;
+ private String organisationId; // ID de l'organisation choisie
+ private String organisationNom; // Nom de l'organisation affichée
+ private boolean accepteReglement = false;
+ private boolean acceptePrelevement = false;
+ private boolean autorisationMarketing = false;
+
+ // Statut de validation
+ private String statutValidation = "EN_ATTENTE"; // EN_ATTENTE, VALIDE, REFUSE
+
+ // Informations complémentaires
+ private String competencesSpeciales;
+ private String centresInteret;
+ private String commentaires;
+
+ // Photo et documents
+ private String photoPath;
+ private List documentsJoints = new ArrayList<>();
+ private org.primefaces.model.file.UploadedFile uploadedPhoto;
+ private String photoBase64;
+
+ public MembreInscriptionBean() {
+ // Initialisation par défaut
+ }
+
+ @PostConstruct
+ public void init() {
+ // Générer un numéro de membre automatiquement
+ this.numeroGenere = "M" + System.currentTimeMillis();
+ }
+
+ // Actions
+ public String inscrire() {
+ try {
+ // Vérifier d'abord si l'organisation peut accepter de nouveaux membres
+ if (!peutAccepterNouveauMembre()) {
+ FacesMessage message = new FacesMessage(FacesMessage.SEVERITY_ERROR,
+ "Quota atteint", "Cette organisation a atteint son quota maximum de membres.");
+ FacesContext.getCurrentInstance().addMessage(null, message);
+ return null;
+ }
+
+ // Créer le DTO membre
+ MembreDTO nouveauMembre = new MembreDTO();
+ nouveauMembre.setNumeroMembre(numeroGenere);
+ nouveauMembre.setNom(nom);
+ nouveauMembre.setPrenom(prenom);
+ nouveauMembre.setEmail(email);
+ nouveauMembre.setTelephone(telephone);
+ nouveauMembre.setDateNaissance(dateNaissance);
+ nouveauMembre.setAdresse(adresse);
+ nouveauMembre.setProfession(profession);
+ nouveauMembre.setStatutMatrimonial(situationMatrimoniale);
+ nouveauMembre.setNationalite(nationalite);
+ nouveauMembre.setStatut(statutValidation); // Statut d'attente par défaut
+ nouveauMembre.setDateInscription(LocalDateTime.now());
+
+ // Validation des données
+ ValidationService.ValidationResult validationResult = validationService.validate(nouveauMembre);
+ if (!validationResult.isValid()) {
+ FacesMessage message = new FacesMessage(FacesMessage.SEVERITY_ERROR,
+ "Erreurs de validation", validationResult.getFirstErrorMessage());
+ FacesContext.getCurrentInstance().addMessage(null, message);
+ return null;
+ }
+
+ // Appel du service REST pour créer le membre
+ MembreDTO membreCreee = membreService.creer(nouveauMembre);
+
+ // Gestion de la photo si disponible
+ if (photoBase64 != null && !photoBase64.trim().isEmpty()) {
+ System.out.println("Photo cadrée reçue: " + photoBase64.length() + " caractères");
+ // TODO: Appeler service de sauvegarde de photo
+ }
+
+ System.out.println("Membre inscrit avec succès: " + membreCreee.getNomComplet());
+
+ // Message de succès
+ FacesMessage message = new FacesMessage(FacesMessage.SEVERITY_INFO,
+ "Inscription soumise", "Votre inscription a été soumise avec succès. Elle sera validée par l'administrateur de votre organisation.");
+ FacesContext.getCurrentInstance().addMessage(null, message);
+
+ return "/pages/public/login?faces-redirect=true";
+
+ } catch (Exception e) {
+ System.err.println("Erreur lors de l'inscription: " + e.getMessage());
+ e.printStackTrace();
+ FacesMessage message = new FacesMessage(FacesMessage.SEVERITY_ERROR,
+ "Erreur", "Erreur lors de l'inscription: " + e.getMessage());
+ FacesContext.getCurrentInstance().addMessage(null, message);
+ return null;
+ }
+ }
+
+ // Méthodes de validation en temps réel
+ public void validateNom() {
+ if (nom != null && !nom.trim().isEmpty()) {
+ ValidationService.ValidationResult result = validationService.validateValue(MembreDTO.class, "nom", nom);
+ if (!result.isValid()) {
+ System.out.println("Erreur validation nom: " + result.getFirstErrorMessage());
+ }
+ }
+ }
+
+ public void validatePrenom() {
+ if (prenom != null && !prenom.trim().isEmpty()) {
+ ValidationService.ValidationResult result = validationService.validateValue(MembreDTO.class, "prenom", prenom);
+ if (!result.isValid()) {
+ System.out.println("Erreur validation prénom: " + result.getFirstErrorMessage());
+ }
+ }
+ }
+
+ public void validateEmail() {
+ if (email != null && !email.trim().isEmpty()) {
+ ValidationService.ValidationResult result = validationService.validateValue(MembreDTO.class, "email", email);
+ if (!result.isValid()) {
+ System.out.println("Erreur validation email: " + result.getFirstErrorMessage());
+ }
+ }
+ }
+
+ public void validateTelephone() {
+ if (telephone != null && !telephone.trim().isEmpty()) {
+ ValidationService.ValidationResult result = validationService.validateValue(MembreDTO.class, "telephone", telephone);
+ if (!result.isValid()) {
+ System.out.println("Erreur validation téléphone: " + result.getFirstErrorMessage());
+ }
+ }
+ }
+
+ public String annuler() {
+ return "/pages/secure/dashboard?faces-redirect=true";
+ }
+
+ public void handleFileUpload(org.primefaces.event.FileUploadEvent event) {
+ // Logique d'upload de documents
+ org.primefaces.model.file.UploadedFile file = event.getFile();
+ if (file != null) {
+ documentsJoints.add(file.getFileName());
+ }
+ }
+
+ public void ajouterDocument() {
+ // Logique d'ajout de document
+ }
+
+ public void supprimerDocument(String document) {
+ documentsJoints.remove(document);
+ }
+
+ public void rechercherParrain() {
+ // Logique de recherche de parrain
+ if (numeroParrain != null && !numeroParrain.trim().isEmpty()) {
+ // Simulation de recherche
+ nomParrain = "Membre trouvé - " + numeroParrain;
+ }
+ }
+
+ public String enregistrerBrouillon() {
+ // Logique d'enregistrement en brouillon
+ return null; // Rester sur la même page
+ }
+
+ // Méthodes pour la progression
+ public boolean isEtapePersonnelleComplete() {
+ return prenom != null && !prenom.trim().isEmpty() &&
+ nom != null && !nom.trim().isEmpty() &&
+ dateNaissance != null &&
+ sexe != null && !sexe.trim().isEmpty();
+ }
+
+ public boolean isEtapeCoordonneeComplete() {
+ return adresse != null && !adresse.trim().isEmpty() &&
+ ville != null && !ville.trim().isEmpty() &&
+ email != null && !email.trim().isEmpty() &&
+ telephoneMobile != null && !telephoneMobile.trim().isEmpty();
+ }
+
+ public boolean isEtapeAdhesionComplete() {
+ return typeAdhesion != null && !typeAdhesion.trim().isEmpty();
+ }
+
+ public boolean isEtapeDocumentsComplete() {
+ return !documentsJoints.isEmpty() || (photoBase64 != null && !photoBase64.trim().isEmpty());
+ }
+
+ public int getProgressionPourcentage() {
+ int etapesCompletes = 0;
+ if (isEtapePersonnelleComplete()) etapesCompletes++;
+ if (isEtapeCoordonneeComplete()) etapesCompletes++;
+ if (isEtapeAdhesionComplete()) etapesCompletes++;
+ if (isEtapeDocumentsComplete()) etapesCompletes++;
+ return (etapesCompletes * 100) / 4;
+ }
+
+ public boolean isFormulaireValide() {
+ return isEtapePersonnelleComplete() &&
+ isEtapeCoordonneeComplete() &&
+ isEtapeAdhesionComplete() &&
+ organisationId != null &&
+ accepteReglement;
+ }
+
+ // Vérification du quota organisation
+ public boolean peutAccepterNouveauMembre() {
+ if (souscriptionBean == null || souscriptionBean.getSouscriptionActive() == null) {
+ return false; // Pas de souscription active
+ }
+ return souscriptionBean.peutAccepterNouveauMembre();
+ }
+
+ public String getMessageQuotaOrganisation() {
+ if (souscriptionBean != null) {
+ return souscriptionBean.getMessageQuota();
+ }
+ return "Informations de quota non disponibles";
+ }
+
+ // Getters et Setters
+ public String getNumeroGenere() { return numeroGenere; }
+ public void setNumeroGenere(String numeroGenere) { this.numeroGenere = numeroGenere; }
+
+ public String getPrenom() { return prenom; }
+ public void setPrenom(String prenom) { this.prenom = prenom; }
+
+ public String getNom() { return nom; }
+ public void setNom(String nom) { this.nom = nom; }
+
+ public String getEmail() { return email; }
+ public void setEmail(String email) { this.email = email; }
+
+ public String getTelephone() { return telephone; }
+ public void setTelephone(String telephone) { this.telephone = telephone; }
+
+ public String getTelephoneMobile() { return telephoneMobile; }
+ public void setTelephoneMobile(String telephoneMobile) { this.telephoneMobile = telephoneMobile; }
+
+ public String getAdresse() { return adresse; }
+ public void setAdresse(String adresse) { this.adresse = adresse; }
+
+ public String getVille() { return ville; }
+ public void setVille(String ville) { this.ville = ville; }
+
+ public String getCodePostal() { return codePostal; }
+ public void setCodePostal(String codePostal) { this.codePostal = codePostal; }
+
+ public String getPays() { return pays; }
+ public void setPays(String pays) { this.pays = pays; }
+
+ public LocalDate getDateNaissance() { return dateNaissance; }
+ public void setDateNaissance(LocalDate dateNaissance) { this.dateNaissance = dateNaissance; }
+
+ public String getLieuNaissance() { return lieuNaissance; }
+ public void setLieuNaissance(String lieuNaissance) { this.lieuNaissance = lieuNaissance; }
+
+ public String getNationalite() { return nationalite; }
+ public void setNationalite(String nationalite) { this.nationalite = nationalite; }
+
+ public String getSexe() { return sexe; }
+ public void setSexe(String sexe) { this.sexe = sexe; }
+
+ public String getSituationMatrimoniale() { return situationMatrimoniale; }
+ public void setSituationMatrimoniale(String situationMatrimoniale) { this.situationMatrimoniale = situationMatrimoniale; }
+
+ public String getProfession() { return profession; }
+ public void setProfession(String profession) { this.profession = profession; }
+
+ public String getEmployeur() { return employeur; }
+ public void setEmployeur(String employeur) { this.employeur = employeur; }
+
+ public String getContactUrgenceNom() { return contactUrgenceNom; }
+ public void setContactUrgenceNom(String contactUrgenceNom) { this.contactUrgenceNom = contactUrgenceNom; }
+
+ public String getContactUrgenceTelephone() { return contactUrgenceTelephone; }
+ public void setContactUrgenceTelephone(String contactUrgenceTelephone) { this.contactUrgenceTelephone = contactUrgenceTelephone; }
+
+ public String getContactUrgenceLien() { return contactUrgenceLien; }
+ public void setContactUrgenceLien(String contactUrgenceLien) { this.contactUrgenceLien = contactUrgenceLien; }
+
+ public String getNumeroBanque() { return numeroBanque; }
+ public void setNumeroBanque(String numeroBanque) { this.numeroBanque = numeroBanque; }
+
+ public String getNomBanque() { return nomBanque; }
+ public void setNomBanque(String nomBanque) { this.nomBanque = nomBanque; }
+
+ public String getRibIban() { return ribIban; }
+ public void setRibIban(String ribIban) { this.ribIban = ribIban; }
+
+ public String getTypeAdhesion() { return typeAdhesion; }
+ public void setTypeAdhesion(String typeAdhesion) { this.typeAdhesion = typeAdhesion; }
+
+ public String getNumeroParrain() { return numeroParrain; }
+ public void setNumeroParrain(String numeroParrain) { this.numeroParrain = numeroParrain; }
+
+ public String getNomParrain() { return nomParrain; }
+ public void setNomParrain(String nomParrain) { this.nomParrain = nomParrain; }
+
+ public String getMotifAdhesion() { return motifAdhesion; }
+ public void setMotifAdhesion(String motifAdhesion) { this.motifAdhesion = motifAdhesion; }
+
+ public boolean isAccepteReglement() { return accepteReglement; }
+ public void setAccepteReglement(boolean accepteReglement) { this.accepteReglement = accepteReglement; }
+
+ public boolean isAcceptePrelevement() { return acceptePrelevement; }
+ public void setAcceptePrelevement(boolean acceptePrelevement) { this.acceptePrelevement = acceptePrelevement; }
+
+ public boolean isAutorisationMarketing() { return autorisationMarketing; }
+ public void setAutorisationMarketing(boolean autorisationMarketing) { this.autorisationMarketing = autorisationMarketing; }
+
+ public String getCompetencesSpeciales() { return competencesSpeciales; }
+ public void setCompetencesSpeciales(String competencesSpeciales) { this.competencesSpeciales = competencesSpeciales; }
+
+ public String getCentresInteret() { return centresInteret; }
+ public void setCentresInteret(String centresInteret) { this.centresInteret = centresInteret; }
+
+ public String getCommentaires() { return commentaires; }
+ public void setCommentaires(String commentaires) { this.commentaires = commentaires; }
+
+ public String getPhotoPath() { return photoPath; }
+ public void setPhotoPath(String photoPath) { this.photoPath = photoPath; }
+
+ public List getDocumentsJoints() { return documentsJoints; }
+ public void setDocumentsJoints(List documentsJoints) { this.documentsJoints = documentsJoints; }
+
+ public org.primefaces.model.file.UploadedFile getUploadedPhoto() { return uploadedPhoto; }
+ public void setUploadedPhoto(org.primefaces.model.file.UploadedFile uploadedPhoto) { this.uploadedPhoto = uploadedPhoto; }
+
+ public String getPhotoBase64() { return photoBase64; }
+ public void setPhotoBase64(String photoBase64) { this.photoBase64 = photoBase64; }
+
+ public String getOrganisationId() { return organisationId; }
+ public void setOrganisationId(String organisationId) { this.organisationId = organisationId; }
+
+ public String getOrganisationNom() { return organisationNom; }
+ public void setOrganisationNom(String organisationNom) { this.organisationNom = organisationNom; }
+
+ public String getStatutValidation() { return statutValidation; }
+ public void setStatutValidation(String statutValidation) { this.statutValidation = statutValidation; }
+
+ // Listes pour les sélections
+ public List getSexeOptions() {
+ List options = new ArrayList<>();
+ options.add("Masculin");
+ options.add("Féminin");
+ return options;
+ }
+
+ public List getSituationMatrimonialeOptions() {
+ List options = new ArrayList<>();
+ options.add("Célibataire");
+ options.add("Marié(e)");
+ options.add("Divorcé(e)");
+ options.add("Veuf(ve)");
+ return options;
+ }
+
+ public List getTypeAdhesionOptions() {
+ List options = new ArrayList<>();
+ options.add("Membre actif");
+ options.add("Membre associé");
+ options.add("Membre bienfaiteur");
+ options.add("Membre honoraire");
+ return options;
+ }
+
+ public List getContactUrgenceLienOptions() {
+ List options = new ArrayList<>();
+ options.add("Conjoint(e)");
+ options.add("Parent");
+ options.add("Enfant");
+ options.add("Frère/Sœur");
+ options.add("Ami(e)");
+ options.add("Autre");
+ return options;
+ }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/MembreListeBean.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/MembreListeBean.java
new file mode 100644
index 0000000..69c6181
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/MembreListeBean.java
@@ -0,0 +1,324 @@
+package dev.lions.unionflow.client.view;
+
+import dev.lions.unionflow.client.dto.MembreDTO;
+import dev.lions.unionflow.client.service.MembreService;
+import jakarta.enterprise.context.SessionScoped;
+import jakarta.inject.Named;
+import jakarta.inject.Inject;
+import jakarta.annotation.PostConstruct;
+import org.eclipse.microprofile.rest.client.inject.RestClient;
+import java.io.Serializable;
+import java.time.LocalDate;
+import java.util.ArrayList;
+import java.util.List;
+import java.util.stream.Collectors;
+
+@Named("membreListeBean")
+@SessionScoped
+public class MembreListeBean implements Serializable {
+
+ private static final long serialVersionUID = 1L;
+
+ @Inject
+ @RestClient
+ MembreService membreService;
+
+ // Statistiques générales
+ private int totalMembres;
+ private int membresActifs;
+ private int cotisationsAJour;
+ private int nouveauxMembres;
+ private int membresInactifs;
+
+ // Filtres
+ private String searchFilter = "";
+ private String statutFilter = "";
+ private String typeFilter = "";
+ private String cotisationFilter = "";
+ private String entiteFilter = "";
+
+ // Filtres avancés
+ private Integer ageMin;
+ private Integer ageMax;
+ private String genreFilter = "";
+ private String villeFilter = "";
+ private LocalDate dateAdhesionDebut;
+ private LocalDate dateAdhesionFin;
+ private String professionFilter = "";
+ private Boolean aDesEnfants;
+
+ // Messages groupés
+ private String sujetMessage;
+ private String contenuMessage;
+ private List canauxMessage = new ArrayList<>();
+
+ // Import/Export
+ private boolean mettreAJourExistants = false;
+ private String formatExport = "EXCEL";
+ private List colonnesExport = new ArrayList<>();
+ private boolean exporterSelection = false;
+
+ // Données
+ private List membres = new ArrayList<>();
+ private List selectedMembres = new ArrayList<>();
+ private List membresFiltres = new ArrayList<>();
+
+ @PostConstruct
+ public void init() {
+ try {
+ chargerMembres();
+ chargerStatistiques();
+ } catch (Exception e) {
+ System.err.println("Erreur lors de l'initialisation: " + e.getMessage());
+ e.printStackTrace();
+ // Données de fallback
+ this.totalMembres = 0;
+ this.membresActifs = 0;
+ this.cotisationsAJour = 0;
+ this.nouveauxMembres = 0;
+ this.membresInactifs = 0;
+ }
+ }
+
+ private void chargerMembres() {
+ try {
+ // Récupération de tous les membres via le service REST
+ membres = membreService.listerTous();
+ membresFiltres = new ArrayList<>(membres);
+
+ System.out.println("Chargement de " + membres.size() + " membres depuis le serveur");
+
+ } catch (Exception e) {
+ System.err.println("Impossible de charger les membres depuis le serveur: " + e.getMessage());
+ // Fallback avec données simulées
+ membres = genererDonneesSimulees();
+ membresFiltres = new ArrayList<>(membres);
+ }
+ }
+
+ private List genererDonneesSimulees() {
+ List membresSimules = new ArrayList<>();
+ for (int i = 1; i <= 20; i++) {
+ MembreDTO membre = new MembreDTO();
+ membre.setId((long) i);
+ membre.setNumeroMembre("M2024" + String.format("%03d", i));
+ membre.setNom("Membre" + i);
+ membre.setPrenom("Prénom" + i);
+ membre.setEmail("membre" + i + "@example.com");
+ membre.setTelephone("77 123 45 " + String.format("%02d", i));
+ membre.setStatut(i % 10 == 0 ? "INACTIF" : "ACTIF");
+ membre.setDateNaissance(LocalDate.now().minusYears(25 + i));
+ membre.setProfession("Profession " + (i % 10 + 1));
+ membre.setAdresse("Adresse " + i);
+ membresSimules.add(membre);
+ }
+ return membresSimules;
+ }
+
+ private void chargerStatistiques() {
+ try {
+ // Récupération des statistiques via le service REST
+ MembreService.StatistiquesMembreDTO stats = membreService.obtenirStatistiques();
+
+ this.totalMembres = stats.getTotalMembres() != null ? stats.getTotalMembres().intValue() : 0;
+ this.membresActifs = stats.getMembresActifs() != null ? stats.getMembresActifs().intValue() : 0;
+ this.membresInactifs = stats.getMembresInactifs() != null ? stats.getMembresInactifs().intValue() : 0;
+ this.nouveauxMembres = stats.getNouveauxMembres30Jours() != null ? stats.getNouveauxMembres30Jours().intValue() : 0;
+
+ // Calcul approximatif des cotisations à jour (à implémenter côté serveur)
+ this.cotisationsAJour = (int) (this.membresActifs * 0.85);
+
+ } catch (Exception e) {
+ System.err.println("Impossible de charger les statistiques: " + e.getMessage());
+ // Utiliser les valeurs de fallback définies dans init()
+ }
+ }
+
+ // Actions de recherche et filtrage
+ public void rechercher() {
+ try {
+ List resultats = membreService.rechercher(
+ searchFilter.isEmpty() ? null : searchFilter, // nom
+ null, // prenom
+ null, // email
+ null, // telephone
+ statutFilter.isEmpty() ? null : statutFilter,
+ null, // associationId
+ 0, // page
+ 100 // size
+ );
+
+ membresFiltres = resultats;
+ System.out.println("Recherche effectuée: " + membresFiltres.size() + " résultats");
+
+ } catch (Exception e) {
+ System.err.println("Erreur lors de la recherche: " + e.getMessage());
+ // En cas d'erreur, appliquer le filtre localement
+ appliquerFiltreLocal();
+ }
+ }
+
+ private void appliquerFiltreLocal() {
+ membresFiltres = membres.stream()
+ .filter(m -> searchFilter.isEmpty() ||
+ m.getNom().toLowerCase().contains(searchFilter.toLowerCase()) ||
+ m.getPrenom().toLowerCase().contains(searchFilter.toLowerCase()) ||
+ m.getEmail().toLowerCase().contains(searchFilter.toLowerCase()))
+ .filter(m -> statutFilter.isEmpty() || m.getStatut().equals(statutFilter))
+ .collect(Collectors.toList());
+ }
+
+ public void reinitialiserFiltres() {
+ searchFilter = "";
+ statutFilter = "";
+ typeFilter = "";
+ cotisationFilter = "";
+ entiteFilter = "";
+ ageMin = null;
+ ageMax = null;
+ genreFilter = "";
+ villeFilter = "";
+ dateAdhesionDebut = null;
+ dateAdhesionFin = null;
+ professionFilter = "";
+ aDesEnfants = null;
+
+ membresFiltres = new ArrayList<>(membres);
+ }
+
+ public void appliquerFiltresAvances() {
+ // Appliquer les filtres avancés
+ System.out.println("Application des filtres avancés");
+ }
+
+ // Import/Export
+ public void importerMembres() {
+ // Logique d'import des membres
+ System.out.println("Import des membres");
+ }
+
+ public void telechargerModele() {
+ // Télécharger modèle d'import
+ System.out.println("Téléchargement du modèle");
+ }
+
+ // Actions avec DTOs
+ public String voirProfil(MembreDTO membre) {
+ return "/pages/secure/membre/profil?id=" + membre.getId() + "&faces-redirect=true";
+ }
+
+ public void activerMembre(MembreDTO membre) {
+ try {
+ membreService.activer(membre.getId());
+ membre.setStatut("ACTIF");
+ System.out.println("Membre activé: " + membre.getNomComplet());
+ } catch (Exception e) {
+ System.err.println("Erreur lors de l'activation: " + e.getMessage());
+ }
+ }
+
+ public void desactiverMembre(MembreDTO membre) {
+ try {
+ membreService.desactiver(membre.getId());
+ membre.setStatut("INACTIF");
+ System.out.println("Membre désactivé: " + membre.getNomComplet());
+ } catch (Exception e) {
+ System.err.println("Erreur lors de la désactivation: " + e.getMessage());
+ }
+ }
+
+ public void exporterMembres() {
+ try {
+ byte[] excelData = membreService.exporterExcel(formatExport, null, statutFilter.isEmpty() ? null : statutFilter);
+ // TODO: Gérer le téléchargement du fichier Excel
+ System.out.println("Export Excel généré: " + excelData.length + " bytes");
+ } catch (Exception e) {
+ System.err.println("Erreur lors de l'export: " + e.getMessage());
+ }
+ }
+
+ // Getters et Setters
+ public int getTotalMembres() { return totalMembres; }
+ public void setTotalMembres(int totalMembres) { this.totalMembres = totalMembres; }
+
+ public int getMembresActifs() { return membresActifs; }
+ public void setMembresActifs(int membresActifs) { this.membresActifs = membresActifs; }
+
+ public int getCotisationsAJour() { return cotisationsAJour; }
+ public void setCotisationsAJour(int cotisationsAJour) { this.cotisationsAJour = cotisationsAJour; }
+
+ public int getNouveauxMembres() { return nouveauxMembres; }
+ public void setNouveauxMembres(int nouveauxMembres) { this.nouveauxMembres = nouveauxMembres; }
+
+ public int getMembresInactifs() { return membresInactifs; }
+ public void setMembresInactifs(int membresInactifs) { this.membresInactifs = membresInactifs; }
+
+ public String getSearchFilter() { return searchFilter; }
+ public void setSearchFilter(String searchFilter) { this.searchFilter = searchFilter; }
+
+ public String getStatutFilter() { return statutFilter; }
+ public void setStatutFilter(String statutFilter) { this.statutFilter = statutFilter; }
+
+ public String getTypeFilter() { return typeFilter; }
+ public void setTypeFilter(String typeFilter) { this.typeFilter = typeFilter; }
+
+ public String getCotisationFilter() { return cotisationFilter; }
+ public void setCotisationFilter(String cotisationFilter) { this.cotisationFilter = cotisationFilter; }
+
+ public String getEntiteFilter() { return entiteFilter; }
+ public void setEntiteFilter(String entiteFilter) { this.entiteFilter = entiteFilter; }
+
+ public Integer getAgeMin() { return ageMin; }
+ public void setAgeMin(Integer ageMin) { this.ageMin = ageMin; }
+
+ public Integer getAgeMax() { return ageMax; }
+ public void setAgeMax(Integer ageMax) { this.ageMax = ageMax; }
+
+ public String getGenreFilter() { return genreFilter; }
+ public void setGenreFilter(String genreFilter) { this.genreFilter = genreFilter; }
+
+ public String getVilleFilter() { return villeFilter; }
+ public void setVilleFilter(String villeFilter) { this.villeFilter = villeFilter; }
+
+ public LocalDate getDateAdhesionDebut() { return dateAdhesionDebut; }
+ public void setDateAdhesionDebut(LocalDate dateAdhesionDebut) { this.dateAdhesionDebut = dateAdhesionDebut; }
+
+ public LocalDate getDateAdhesionFin() { return dateAdhesionFin; }
+ public void setDateAdhesionFin(LocalDate dateAdhesionFin) { this.dateAdhesionFin = dateAdhesionFin; }
+
+ public String getProfessionFilter() { return professionFilter; }
+ public void setProfessionFilter(String professionFilter) { this.professionFilter = professionFilter; }
+
+ public Boolean getADesEnfants() { return aDesEnfants; }
+ public void setADesEnfants(Boolean aDesEnfants) { this.aDesEnfants = aDesEnfants; }
+
+ public String getSujetMessage() { return sujetMessage; }
+ public void setSujetMessage(String sujetMessage) { this.sujetMessage = sujetMessage; }
+
+ public String getContenuMessage() { return contenuMessage; }
+ public void setContenuMessage(String contenuMessage) { this.contenuMessage = contenuMessage; }
+
+ public List getCanauxMessage() { return canauxMessage; }
+ public void setCanauxMessage(List canauxMessage) { this.canauxMessage = canauxMessage; }
+
+ public boolean isMettreAJourExistants() { return mettreAJourExistants; }
+ public void setMettreAJourExistants(boolean mettreAJourExistants) { this.mettreAJourExistants = mettreAJourExistants; }
+
+ public String getFormatExport() { return formatExport; }
+ public void setFormatExport(String formatExport) { this.formatExport = formatExport; }
+
+ public List getColonnesExport() { return colonnesExport; }
+ public void setColonnesExport(List colonnesExport) { this.colonnesExport = colonnesExport; }
+
+ public boolean isExporterSelection() { return exporterSelection; }
+ public void setExporterSelection(boolean exporterSelection) { this.exporterSelection = exporterSelection; }
+
+ public List getMembres() { return membresFiltres; }
+ public void setMembres(List membres) { this.membres = membres; }
+
+ public List getSelectedMembres() { return selectedMembres; }
+ public void setSelectedMembres(List selectedMembres) { this.selectedMembres = selectedMembres; }
+
+ public List getMembresFiltres() { return membresFiltres; }
+ public void setMembresFiltres(List membresFiltres) { this.membresFiltres = membresFiltres; }
+}
\ No newline at end of file
diff --git a/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/MembreProfilBean.java b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/MembreProfilBean.java
new file mode 100644
index 0000000..258e5e4
--- /dev/null
+++ b/unionflow-client-quarkus-primefaces-freya/src/main/java/dev/lions/unionflow/client/view/MembreProfilBean.java
@@ -0,0 +1,742 @@
+package dev.lions.unionflow.client.view;
+
+import jakarta.enterprise.context.SessionScoped;
+import jakarta.inject.Named;
+import jakarta.annotation.PostConstruct;
+import java.io.Serializable;
+import java.time.LocalDate;
+import java.time.LocalDateTime;
+import java.util.ArrayList;
+import java.util.List;
+import org.primefaces.event.FileUploadEvent;
+
+@Named("membreProfilBean")
+@SessionScoped
+public class MembreProfilBean implements Serializable {
+
+ private static final long serialVersionUID = 1L;
+
+ private Membre membre;
+ private Membre membreEdit;
+ private Statistiques statistiques;
+ private CotisationsData cotisations;
+ private EvenementsData evenements;
+ private AidesData aides;
+ private DemandesData demandes;
+ private HistoriqueData historique;
+ private ContactData contact;
+ private Long membreId;
+
+ @PostConstruct
+ public void init() {
+ if (membreId == null) {
+ membreId = 1L; // Par défaut pour le test
+ }
+ chargerMembre();
+ chargerStatistiques();
+ chargerCotisations();
+ chargerEvenements();
+ chargerAides();
+ chargerDemandes();
+ chargerHistorique();
+ initContact();
+ }
+
+ private void chargerMembre() {
+ membre = new Membre();
+ membre.setId(membreId);
+ membre.setNumeroMembre("M2024001");
+ membre.setPrenom("Jean");
+ membre.setNom("DIALLO");
+ membre.setEmail("jean.diallo@email.com");
+ membre.setTelephone("77 123 45 67");
+ membre.setDateNaissance(LocalDate.of(1985, 6, 15));
+ membre.setGenre("Masculin");
+ membre.setSituationFamiliale("Marié");
+ membre.setProfession("Ingénieur Informatique");
+ membre.setAdresse("Villa n°123, Cité Keur Gorgui");
+ membre.setVille("Dakar");
+ membre.setPays("Sénégal");
+ membre.setTypeMembre("ACTIF");
+ membre.setStatut("ACTIF");
+ membre.setEntite("LIONS CLUB Dakar Métropole");
+ membre.setDateAdhesion(LocalDate.of(2020, 3, 15));
+ membre.setCotisationStatut("À jour");
+ membre.setTauxParticipation(85);
+
+ // Famille
+ List famille = new ArrayList<>();
+ MembreFamille epouse = new MembreFamille();
+ epouse.setNomComplet("Awa DIALLO");
+ epouse.setRelation("Épouse");
+ epouse.setDateNaissance(LocalDate.of(1987, 9, 20));
+ epouse.setBeneficiaire(true);
+ famille.add(epouse);
+
+ MembreFamille enfant1 = new MembreFamille();
+ enfant1.setNomComplet("Amadou DIALLO");
+ enfant1.setRelation("Fils");
+ enfant1.setDateNaissance(LocalDate.of(2010, 12, 5));
+ enfant1.setBeneficiaire(true);
+ famille.add(enfant1);
+
+ membre.setFamille(famille);
+
+ // Copie pour l'édition
+ membreEdit = new Membre();
+ copierMembre(membre, membreEdit);
+ }
+
+ private void chargerStatistiques() {
+ statistiques = new Statistiques();
+ statistiques.setEvenementsParticipes(24);
+ statistiques.setCotisationsPayees(12);
+ statistiques.setAidesRecues(2);
+ statistiques.setScoreEngagement(95);
+ statistiques.setTauxParticipation(85);
+ statistiques.setEvenementsAnnee(8);
+ statistiques.setEvenementsTotal(24);
+ statistiques.setEvenementsOrganises(3);
+ statistiques.setAbsences(2);
+ }
+
+ private void chargerCotisations() {
+ cotisations = new CotisationsData();
+ cotisations.setStatutActuel("À jour");
+ cotisations.setStatutSeverity("success");
+ cotisations.setDernierPaiement("15/07/2024");
+ cotisations.setProchaineEcheance("15/08/2024");
+ cotisations.setProchaineEcheanceClass("text-green-500");
+ cotisations.setTotalAnnee("120 000 FCFA");
+
+ // Historique des paiements
+ List historique = new ArrayList<>();
+ for (int i = 1; i <= 6; i++) {
+ PaiementCotisation paiement = new PaiementCotisation();
+ paiement.setDate(LocalDate.now().minusMonths(i));
+ paiement.setMontant(10000.0);
+ paiement.setModePaiement(i % 2 == 0 ? "Wave Money" : "Espèces");
+ paiement.setModeIcon(i % 2 == 0 ? "pi-mobile" : "pi-money-bill");
+ paiement.setStatut("Validé");
+ paiement.setStatutSeverity("success");
+ historique.add(paiement);
+ }
+ cotisations.setHistorique(historique);
+ }
+
+ private void chargerEvenements() {
+ evenements = new EvenementsData();
+ List recents = new ArrayList<>();
+
+ String[] titres = {"Réunion mensuelle", "Action humanitaire", "Formation leadership", "Collecte de fonds"};
+ String[] lieux = {"Hôtel Radisson", "École Primaire", "Centre de formation", "Stade Léopold Sédar Senghor"};
+ String[] types = {"REUNION", "ACTION", "FORMATION", "COLLECTE"};
+
+ for (int i = 0; i < 4; i++) {
+ EvenementParticipation evt = new EvenementParticipation();
+ evt.setTitre(titres[i]);
+ evt.setDate(LocalDate.now().minusDays(i * 7).toString());
+ evt.setLieu(lieux[i]);
+ evt.setParticipation(i < 3 ? "Présent" : "Absent");
+ evt.setParticipationSeverity(i < 3 ? "success" : "danger");
+ evt.setRole(i == 0 ? "Organisateur" : "Participant");
+ evt.setTypeIcon("pi-calendar");
+ evt.setTypeColorClass("bg-blue-500");
+ recents.add(evt);
+ }
+ evenements.setRecents(recents);
+ }
+
+ private void chargerAides() {
+ aides = new AidesData();
+ List recues = new ArrayList<>();
+
+ Aide aide1 = new Aide();
+ aide1.setType("Aide médicale");
+ aide1.setMontant(50000.0);
+ aide1.setDate(LocalDate.of(2024, 5, 10));
+ aide1.setStatut("Validée");
+ aide1.setStatutSeverity("success");
+ aide1.setTypeIcon("pi-heart");
+ aide1.setTypeColor("text-red-500");
+ recues.add(aide1);
+
+ Aide aide2 = new Aide();
+ aide2.setType("Aide scolaire");
+ aide2.setMontant(25000.0);
+ aide2.setDate(LocalDate.of(2024, 1, 15));
+ aide2.setStatut("Validée");
+ aide2.setStatutSeverity("success");
+ aide2.setTypeIcon("pi-book");
+ aide2.setTypeColor("text-blue-500");
+ recues.add(aide2);
+
+ aides.setRecues(recues);
+ }
+
+ private void chargerDemandes() {
+ demandes = new DemandesData();
+ List enCours = new ArrayList<>();
+
+ Demande demande1 = new Demande();
+ demande1.setType("Certificat");
+ demande1.setObjet("Certificat d'adhésion");
+ demande1.setDateDepot(LocalDate.now().minusDays(3));
+ demande1.setStatut("En cours");
+ demande1.setStatutSeverity("warning");
+ enCours.add(demande1);
+
+ demandes.setEnCours(enCours);
+ }
+
+ private void chargerHistorique() {
+ historique = new HistoriqueData();
+ List activites = new ArrayList<>();
+
+ String[] descriptions = {
+ "Profil mis à jour",
+ "Participation à la réunion mensuelle",
+ "Paiement de cotisation validé",
+ "Nouvelle adhésion enregistrée"
+ };
+
+ for (int i = 0; i < 4; i++) {
+ Activite activite = new Activite();
+ activite.setDescription(descriptions[i]);
+ activite.setDate(LocalDateTime.now().minusDays(i * 2).toString());
+ activite.setAuteur(i == 0 ? "Jean DIALLO" : "Admin");
+ activite.setIcone(i % 2 == 0 ? "pi-user" : "pi-calendar");
+ activite.setCouleur(i % 2 == 0 ? "text-blue-500" : "text-green-500");
+ if (i == 2) {
+ activite.setDetails("Montant: 10 000 FCFA via Wave Money");
+ }
+ activites.add(activite);
+ }
+ historique.setActivites(activites);
+ }
+
+ private void initContact() {
+ contact = new ContactData();
+ contact.setCanaux(new ArrayList<>());
+ }
+
+ // Actions
+ public void changerPhoto(FileUploadEvent event) {
+ // Logique de changement de photo
+ System.out.println("Photo changée: " + event.getFile().getFileName());
+ }
+
+ public String gererCotisations() {
+ return "/pages/secure/membre/cotisations?id=" + membre.getId() + "&faces-redirect=true";
+ }
+
+ public void sauvegarderModifications() {
+ copierMembre(membreEdit, membre);
+ System.out.println("Profil mis à jour pour: " + membre.getNomComplet());
+ }
+
+ public void envoyerMessage() {
+ System.out.println("Message envoyé: " + contact.getSujet() + " via " + contact.getCanaux());
+ contact = new ContactData();
+ contact.setCanaux(new ArrayList<>());
+ }
+
+ public void envoyerRappelCotisation() {
+ System.out.println("Rappel de cotisation envoyé à: " + membre.getEmail());
+ }
+
+ public void suspendre() {
+ membre.setStatut("SUSPENDU");
+ System.out.println("Membre suspendu: " + membre.getNomComplet());
+ }
+
+ public void reactiver() {
+ membre.setStatut("ACTIF");
+ System.out.println("Membre réactivé: " + membre.getNomComplet());
+ }
+
+ public void exporterDonnees() {
+ System.out.println("Export des données pour: " + membre.getNomComplet());
+ }
+
+ public String supprimer() {
+ System.out.println("Membre supprimé: " + membre.getNomComplet());
+ return "/pages/secure/membre/liste?faces-redirect=true";
+ }
+
+ private void copierMembre(Membre source, Membre destination) {
+ destination.setId(source.getId());
+ destination.setPrenom(source.getPrenom());
+ destination.setNom(source.getNom());
+ destination.setEmail(source.getEmail());
+ destination.setTelephone(source.getTelephone());
+ destination.setDateNaissance(source.getDateNaissance());
+ destination.setProfession(source.getProfession());
+ destination.setAdresse(source.getAdresse());
+ }
+
+ // Getters et Setters
+ public Membre getMembre() { return membre; }
+ public void setMembre(Membre membre) { this.membre = membre; }
+
+ public Membre getMembreEdit() { return membreEdit; }
+ public void setMembreEdit(Membre membreEdit) { this.membreEdit = membreEdit; }
+
+ public Statistiques getStatistiques() { return statistiques; }
+ public void setStatistiques(Statistiques statistiques) { this.statistiques = statistiques; }
+
+ public CotisationsData getCotisations() { return cotisations; }
+ public void setCotisations(CotisationsData cotisations) { this.cotisations = cotisations; }
+
+ public EvenementsData getEvenements() { return evenements; }
+ public void setEvenements(EvenementsData evenements) { this.evenements = evenements; }
+
+ public AidesData getAides() { return aides; }
+ public void setAides(AidesData aides) { this.aides = aides; }
+
+ public DemandesData getDemandes() { return demandes; }
+ public void setDemandes(DemandesData demandes) { this.demandes = demandes; }
+
+ public HistoriqueData getHistorique() { return historique; }
+ public void setHistorique(HistoriqueData historique) { this.historique = historique; }
+
+ public ContactData getContact() { return contact; }
+ public void setContact(ContactData contact) { this.contact = contact; }
+
+ public Long getMembreId() { return membreId; }
+ public void setMembreId(Long membreId) { this.membreId = membreId; }
+
+ // Classes internes
+ public static class Membre {
+ private Long id;
+ private String numeroMembre;
+ private String prenom;
+ private String nom;
+ private String email;
+ private String telephone;
+ private LocalDate dateNaissance;
+ private String genre;
+ private String situationFamiliale;
+ private String profession;
+ private String adresse;
+ private String ville;
+ private String pays;
+ private String typeMembre;
+ private String statut;
+ private String entite;
+ private LocalDate dateAdhesion;
+ private String cotisationStatut;
+ private int tauxParticipation;
+ private String photoUrl;
+ private List famille = new ArrayList<>();
+
+ // Getters et setters
+ public Long getId() { return id; }
+ public void setId(Long id) { this.id = id; }
+
+ public String getNumeroMembre() { return numeroMembre; }
+ public void setNumeroMembre(String numeroMembre) { this.numeroMembre = numeroMembre; }
+
+ public String getPrenom() { return prenom; }
+ public void setPrenom(String prenom) { this.prenom = prenom; }
+
+ public String getNom() { return nom; }
+ public void setNom(String nom) { this.nom = nom; }
+
+ public String getEmail() { return email; }
+ public void setEmail(String email) { this.email = email; }
+
+ public String getTelephone() { return telephone; }
+ public void setTelephone(String telephone) { this.telephone = telephone; }
+
+ public LocalDate getDateNaissance() { return dateNaissance; }
+ public void setDateNaissance(LocalDate dateNaissance) { this.dateNaissance = dateNaissance; }
+
+ public String getGenre() { return genre; }
+ public void setGenre(String genre) { this.genre = genre; }
+
+ public String getSituationFamiliale() { return situationFamiliale; }
+ public void setSituationFamiliale(String situationFamiliale) { this.situationFamiliale = situationFamiliale; }
+
+ public String getProfession() { return profession; }
+ public void setProfession(String profession) { this.profession = profession; }
+
+ public String getAdresse() { return adresse; }
+ public void setAdresse(String adresse) { this.adresse = adresse; }
+
+ public String getVille() { return ville; }
+ public void setVille(String ville) { this.ville = ville; }
+
+ public String getPays() { return pays; }
+ public void setPays(String pays) { this.pays = pays; }
+
+ public String getTypeMembre() { return typeMembre; }
+ public void setTypeMembre(String typeMembre) { this.typeMembre = typeMembre; }
+
+ public String getStatut() { return statut; }
+ public void setStatut(String statut) { this.statut = statut; }
+
+ public String getEntite() { return entite; }
+ public void setEntite(String entite) { this.entite = entite; }
+
+ public LocalDate getDateAdhesion() { return dateAdhesion; }
+ public void setDateAdhesion(LocalDate dateAdhesion) { this.dateAdhesion = dateAdhesion; }
+
+ public String getCotisationStatut() { return cotisationStatut; }
+ public void setCotisationStatut(String cotisationStatut) { this.cotisationStatut = cotisationStatut; }
+
+ public int getTauxParticipation() { return tauxParticipation; }
+ public void setTauxParticipation(int tauxParticipation) { this.tauxParticipation = tauxParticipation; }
+
+ public String getPhotoUrl() { return photoUrl; }
+ public void setPhotoUrl(String photoUrl) { this.photoUrl = photoUrl; }
+
+ public List getFamille() { return famille; }
+ public void setFamille(List famille) { this.famille = famille; }
+
+ // Propriétés dérivées
+ public String getNomComplet() {
+ return prenom + " " + nom;
+ }
+
+ public String getInitiales() {
+ return (prenom != null ? prenom.substring(0, 1) : "") +
+ (nom != null ? nom.substring(0, 1) : "");
+ }
+
+ public String getStatutSeverity() {
+ return switch (statut) {
+ case "ACTIF" -> "success";
+ case "INACTIF" -> "warning";
+ case "SUSPENDU" -> "danger";
+ case "RADIE" -> "danger";
+ default -> "secondary";
+ };
+ }
+
+ public String getStatutIcon() {
+ return switch (statut) {
+ case "ACTIF" -> "pi-check";
+ case "INACTIF" -> "pi-pause";
+ case "SUSPENDU" -> "pi-ban";
+ case "RADIE" -> "pi-times";
+ default -> "pi-circle";
+ };
+ }
+
+ public String getTypeSeverity() {
+ return switch (typeMembre) {
+ case "ACTIF" -> "info";
+ case "ASSOCIE" -> "success";
+ case "BIENFAITEUR" -> "warning";
+ case "HONORAIRE" -> "secondary";
+ default -> "info";
+ };
+ }
+
+ public String getTypeIcon() {
+ return switch (typeMembre) {
+ case "ACTIF" -> "pi-user";
+ case "ASSOCIE" -> "pi-users";
+ case "BIENFAITEUR" -> "pi-star";
+ case "HONORAIRE" -> "pi-crown";
+ default -> "pi-user";
+ };
+ }
+
+ public String getAnciennete() {
+ if (dateAdhesion == null) return "N/A";
+ long mois = java.time.temporal.ChronoUnit.MONTHS.between(dateAdhesion, LocalDate.now());
+ if (mois < 12) return mois + " mois";
+ return (mois / 12) + " an" + (mois / 12 > 1 ? "s" : "");
+ }
+
+ public String getCotisationColor() {
+ return cotisationStatut != null && cotisationStatut.equals("À jour") ? "text-green-500" : "text-red-500";
+ }
+ }
+
+ public static class MembreFamille {
+ private String nomComplet;
+ private String relation;
+ private LocalDate dateNaissance;
+ private boolean beneficiaire;
+
+ // Getters et setters
+ public String getNomComplet() { return nomComplet; }
+ public void setNomComplet(String nomComplet) { this.nomComplet = nomComplet; }
+
+ public String getRelation() { return relation; }
+ public void setRelation(String relation) { this.relation = relation; }
+
+ public LocalDate getDateNaissance() { return dateNaissance; }
+ public void setDateNaissance(LocalDate dateNaissance) { this.dateNaissance = dateNaissance; }
+
+ public boolean isBeneficiaire() { return beneficiaire; }
+ public void setBeneficiaire(boolean beneficiaire) { this.beneficiaire = beneficiaire; }
+ }
+
+ public static class Statistiques {
+ private int evenementsParticipes;
+ private int cotisationsPayees;
+ private int aidesRecues;
+ private int scoreEngagement;
+ private int tauxParticipation;
+ private int evenementsAnnee;
+ private int evenementsTotal;
+ private int evenementsOrganises;
+ private int absences;
+
+ // Getters et setters
+ public int getEvenementsParticipes() { return evenementsParticipes; }
+ public void setEvenementsParticipes(int evenementsParticipes) { this.evenementsParticipes = evenementsParticipes; }
+
+ public int getCotisationsPayees() { return cotisationsPayees; }
+ public void setCotisationsPayees(int cotisationsPayees) { this.cotisationsPayees = cotisationsPayees; }
+
+ public int getAidesRecues() { return aidesRecues; }
+ public void setAidesRecues(int aidesRecues) { this.aidesRecues = aidesRecues; }
+
+ public int getScoreEngagement() { return scoreEngagement; }
+ public void setScoreEngagement(int scoreEngagement) { this.scoreEngagement = scoreEngagement; }
+
+ public int getTauxParticipation() { return tauxParticipation; }
+ public void setTauxParticipation(int tauxParticipation) { this.tauxParticipation = tauxParticipation; }
+
+ public int getEvenementsAnnee() { return evenementsAnnee; }
+ public void setEvenementsAnnee(int evenementsAnnee) { this.evenementsAnnee = evenementsAnnee; }
+
+ public int getEvenementsTotal() { return evenementsTotal; }
+ public void setEvenementsTotal(int evenementsTotal) { this.evenementsTotal = evenementsTotal; }
+
+ public int getEvenementsOrganises() { return evenementsOrganises; }
+ public void setEvenementsOrganises(int evenementsOrganises) { this.evenementsOrganises = evenementsOrganises; }
+
+ public int getAbsences() { return absences; }
+ public void setAbsences(int absences) { this.absences = absences; }
+ }
+
+ public static class CotisationsData {
+ private String statutActuel;
+ private String statutSeverity;
+ private String dernierPaiement;
+ private String prochaineEcheance;
+ private String prochaineEcheanceClass;
+ private String totalAnnee;
+ private List historique = new ArrayList<>();
+
+ // Getters et setters
+ public String getStatutActuel() { return statutActuel; }
+ public void setStatutActuel(String statutActuel) { this.statutActuel = statutActuel; }
+
+ public String getStatutSeverity() { return statutSeverity; }
+ public void setStatutSeverity(String statutSeverity) { this.statutSeverity = statutSeverity; }
+
+ public String getDernierPaiement() { return dernierPaiement; }
+ public void setDernierPaiement(String dernierPaiement) { this.dernierPaiement = dernierPaiement; }
+
+ public String getProchaineEcheance() { return prochaineEcheance; }
+ public void setProchaineEcheance(String prochaineEcheance) { this.prochaineEcheance = prochaineEcheance; }
+
+ public String getProchaineEcheanceClass() { return prochaineEcheanceClass; }
+ public void setProchaineEcheanceClass(String prochaineEcheanceClass) { this.prochaineEcheanceClass = prochaineEcheanceClass; }
+
+ public String getTotalAnnee() { return totalAnnee; }
+ public void setTotalAnnee(String totalAnnee) { this.totalAnnee = totalAnnee; }
+
+ public List getHistorique() { return historique; }
+ public void setHistorique(List historique) { this.historique = historique; }
+ }
+
+ public static class PaiementCotisation {
+ private LocalDate date;
+ private Double montant;
+ private String modePaiement;
+ private String modeIcon;
+ private String statut;
+ private String statutSeverity;
+
+ // Getters et setters
+ public LocalDate getDate() { return date; }
+ public void setDate(LocalDate date) { this.date = date; }
+
+ public Double getMontant() { return montant; }
+ public void setMontant(Double montant) { this.montant = montant; }
+
+ public String getModePaiement() { return modePaiement; }
+ public void setModePaiement(String modePaiement) { this.modePaiement = modePaiement; }
+
+ public String getModeIcon() { return modeIcon; }
+ public void setModeIcon(String modeIcon) { this.modeIcon = modeIcon; }
+
+ public String getStatut() { return statut; }
+ public void setStatut(String statut) { this.statut = statut; }
+
+ public String getStatutSeverity() { return statutSeverity; }
+ public void setStatutSeverity(String statutSeverity) { this.statutSeverity = statutSeverity; }
+ }
+
+ public static class EvenementsData {
+ private List recents = new ArrayList<>();
+
+ public List getRecents() { return recents; }
+ public void setRecents(List recents) { this.recents = recents; }
+ }
+
+ public static class EvenementParticipation {
+ private String titre;
+ private String date;
+ private String lieu;
+ private String participation;
+ private String participationSeverity;
+ private String role;
+ private String typeIcon;
+ private String typeColorClass;
+
+ // Getters et setters
+ public String getTitre() { return titre; }
+ public void setTitre(String titre) { this.titre = titre; }
+
+ public String getDate() { return date; }
+ public void setDate(String date) { this.date = date; }
+
+ public String getLieu() { return lieu; }
+ public void setLieu(String lieu) { this.lieu = lieu; }
+
+ public String getParticipation() { return participation; }
+ public void setParticipation(String participation) { this.participation = participation; }
+
+ public String getParticipationSeverity() { return participationSeverity; }
+ public void setParticipationSeverity(String participationSeverity) { this.participationSeverity = participationSeverity; }
+
+ public String getRole() { return role; }
+ public void setRole(String role) { this.role = role; }
+
+ public String getTypeIcon() { return typeIcon; }
+ public void setTypeIcon(String typeIcon) { this.typeIcon = typeIcon; }
+
+ public String getTypeColorClass() { return typeColorClass; }
+ public void setTypeColorClass(String typeColorClass) { this.typeColorClass = typeColorClass; }
+ }
+
+ public static class AidesData {
+ private List recues = new ArrayList<>();
+
+ public List getRecues() { return recues; }
+ public void setRecues(List recues) { this.recues = recues; }
+ }
+
+ public static class Aide {
+ private String type;
+ private Double montant;
+ private LocalDate date;
+ private String statut;
+ private String statutSeverity;
+ private String typeIcon;
+ private String typeColor;
+
+ // Getters et setters
+ public String getType() { return type; }
+ public void setType(String type) { this.type = type; }
+
+ public Double getMontant() { return montant; }
+ public void setMontant(Double montant) { this.montant = montant; }
+
+ public LocalDate getDate() { return date; }
+ public void setDate(LocalDate date) { this.date = date; }
+
+ public String getStatut() { return statut; }
+ public void setStatut(String statut) { this.statut = statut; }
+
+ public String getStatutSeverity() { return statutSeverity; }
+ public void setStatutSeverity(String statutSeverity) { this.statutSeverity = statutSeverity; }
+
+ public String getTypeIcon() { return typeIcon; }
+ public void setTypeIcon(String typeIcon) { this.typeIcon = typeIcon; }
+
+ public String getTypeColor() { return typeColor; }
+ public void setTypeColor(String typeColor) { this.typeColor = typeColor; }
+ }
+
+ public static class DemandesData {
+ private List enCours = new ArrayList<>();
+
+ public List getEnCours() { return enCours; }
+ public void setEnCours(List enCours) { this.enCours = enCours; }
+ }
+
+ public static class Demande {
+ private String type;
+ private String objet;
+ private LocalDate dateDepot;
+ private String statut;
+ private String statutSeverity;
+
+ // Getters et setters
+ public String getType() { return type; }
+ public void setType(String type) { this.type = type; }
+
+ public String getObjet() { return objet; }
+ public void setObjet(String objet) { this.objet = objet; }
+
+ public LocalDate getDateDepot() { return dateDepot; }
+ public void setDateDepot(LocalDate dateDepot) { this.dateDepot = dateDepot; }
+
+ public String getStatut() { return statut; }
+ public void setStatut(String statut) { this.statut = statut; }
+
+ public String getStatutSeverity() { return statutSeverity; }
+ public void setStatutSeverity(String statutSeverity) { this.statutSeverity = statutSeverity; }
+ }
+
+ public static class HistoriqueData {
+ private List activites = new ArrayList<>();
+
+ public List getActivites() { return activites; }
+ public void setActivites(List activites) { this.activites = activites; }
+ }
+
+ public static class Activite {
+ private String description;
+ private String date;
+ private String auteur;
+ private String icone;
+ private String couleur;
+ private String details;
+
+ // Getters et setters
+ public String getDescription() { return description; }
+ public void setDescription(String description) { this.description = description; }
+
+ public String getDate() { return date; }
+ public void setDate(String date) { this.date = date; }
+
+ public String getAuteur() { return auteur; }
+ public void setAuteur(String auteur) { this.auteur = auteur; }
+
+ 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 getDetails() { return details; }
+ public void setDetails(String details) { this.details = details; }
+ }
+
+ public static class ContactData {
+ private String sujet;
+ private String message;
+ private List canaux = new ArrayList<>();
+
+ // Getters et setters
+ public String getSujet() { return sujet; }
+ public void setSujet(String sujet) { this.sujet = sujet; }
+
+ public String getMessage() { return message; }
+ public void setMessage(String message) { this.message = message; }
+
+ public List