From f11d1e62b4300ad6d381ef8939ecd488edf076d1 Mon Sep 17 00:00:00 2001 From: Soriba SYLLA Date: Fri, 19 Dec 2025 09:43:33 +0000 Subject: [PATCH] Mon commit initial --- .gitignore | 3 + SGL/__init__.py | 0 SGL/__pycache__/__init__.cpython-310.pyc | Bin 0 -> 135 bytes SGL/__pycache__/__init__.cpython-313.pyc | Bin 0 -> 157 bytes SGL/__pycache__/settings.cpython-310.pyc | Bin 0 -> 2739 bytes SGL/__pycache__/settings.cpython-313.pyc | Bin 0 -> 3087 bytes SGL/__pycache__/urls.cpython-310.pyc | Bin 0 -> 1958 bytes SGL/__pycache__/urls.cpython-313.pyc | Bin 0 -> 2488 bytes SGL/__pycache__/views.cpython-310.pyc | Bin 0 -> 8530 bytes SGL/__pycache__/views.cpython-313.pyc | Bin 0 -> 11371 bytes SGL/__pycache__/wsgi.cpython-310.pyc | Bin 0 -> 530 bytes SGL/__pycache__/wsgi.cpython-313.pyc | Bin 0 -> 630 bytes SGL/asgi.py | 16 + SGL/settings.py | 147 ++++ SGL/templates/BASE.html | 114 +++ SGL/templates/emails/email_template.html | 20 + SGL/templates/emails/téléchargement.png | Bin 0 -> 4808 bytes .../emails/téléchargement.png:Zone.Identifier | Bin 0 -> 25 bytes SGL/templates/index.html | 206 ++++++ SGL/urls.py | 68 ++ SGL/views.py | 334 +++++++++ SGL/wsgi.py | 16 + authentification/__init__.py | 0 .../__pycache__/__init__.cpython-310.pyc | Bin 0 -> 148 bytes .../__pycache__/__init__.cpython-313.pyc | Bin 0 -> 164 bytes .../__pycache__/admin.cpython-310.pyc | Bin 0 -> 189 bytes .../__pycache__/admin.cpython-313.pyc | Bin 0 -> 208 bytes .../__pycache__/apps.cpython-310.pyc | Bin 0 -> 447 bytes .../__pycache__/apps.cpython-313.pyc | Bin 0 -> 548 bytes .../__pycache__/models.cpython-310.pyc | Bin 0 -> 1736 bytes .../__pycache__/models.cpython-313.pyc | Bin 0 -> 2303 bytes .../__pycache__/tests.cpython-313.pyc | Bin 0 -> 208 bytes .../__pycache__/urls.cpython-310.pyc | Bin 0 -> 418 bytes .../__pycache__/urls.cpython-313.pyc | Bin 0 -> 519 bytes .../__pycache__/views.cpython-310.pyc | Bin 0 -> 1127 bytes .../__pycache__/views.cpython-313.pyc | Bin 0 -> 1446 bytes authentification/admin.py | 3 + authentification/apps.py | 6 + authentification/migrations/0001_initial.py | 33 + authentification/migrations/__init__.py | 0 .../__pycache__/0001_initial.cpython-310.pyc | Bin 0 -> 1197 bytes .../__pycache__/0001_initial.cpython-313.pyc | Bin 0 -> 1943 bytes .../__pycache__/__init__.cpython-310.pyc | Bin 0 -> 159 bytes .../__pycache__/__init__.cpython-313.pyc | Bin 0 -> 175 bytes authentification/models.py | 39 ++ .../templates/authentification/login.html | 40 ++ authentification/templatetags/__init__.py | 0 .../__pycache__/__init__.cpython-310.pyc | Bin 0 -> 161 bytes .../__pycache__/__init__.cpython-313.pyc | Bin 0 -> 177 bytes .../__pycache__/group_tags.cpython-313.pyc | Bin 0 -> 596 bytes .../__pycache__/sorel.cpython-313.pyc | Bin 0 -> 591 bytes .../tags_personnaliser.cpython-310.pyc | Bin 0 -> 815 bytes .../tags_personnaliser.cpython-313.pyc | Bin 0 -> 1411 bytes .../templatetags/tags_personnaliser.py | 29 + authentification/tests.py | 3 + authentification/urls.py | 11 + authentification/views.py | 34 + gestion_fournisseur/__init__.py | 0 .../__pycache__/__init__.cpython-310.pyc | Bin 0 -> 151 bytes .../__pycache__/__init__.cpython-313.pyc | Bin 0 -> 173 bytes .../__pycache__/admin.cpython-310.pyc | Bin 0 -> 192 bytes .../__pycache__/admin.cpython-313.pyc | Bin 0 -> 211 bytes .../__pycache__/apps.cpython-310.pyc | Bin 0 -> 455 bytes .../__pycache__/apps.cpython-313.pyc | Bin 0 -> 556 bytes .../__pycache__/forms.cpython-310.pyc | Bin 0 -> 1124 bytes .../__pycache__/forms.cpython-313.pyc | Bin 0 -> 1517 bytes .../__pycache__/models.cpython-310.pyc | Bin 0 -> 340 bytes .../__pycache__/models.cpython-313.pyc | Bin 0 -> 361 bytes .../__pycache__/tests.cpython-313.pyc | Bin 0 -> 211 bytes .../__pycache__/urls.cpython-310.pyc | Bin 0 -> 872 bytes .../__pycache__/urls.cpython-313.pyc | Bin 0 -> 1113 bytes .../__pycache__/views.cpython-310.pyc | Bin 0 -> 4934 bytes .../__pycache__/views.cpython-313.pyc | Bin 0 -> 6385 bytes gestion_fournisseur/admin.py | 3 + gestion_fournisseur/apps.py | 6 + gestion_fournisseur/forms.py | 34 + gestion_fournisseur/migrations/__init__.py | 0 .../__pycache__/0001_initial.cpython-313.pyc | Bin 0 -> 1876 bytes ...fournisseur_email_and_more.cpython-313.pyc | Bin 0 -> 2089 bytes ...orie_fournisseur_categorie.cpython-313.pyc | Bin 0 -> 1068 bytes ...lter_fournisseur_telephone.cpython-313.pyc | Bin 0 -> 932 bytes .../__pycache__/__init__.cpython-310.pyc | Bin 0 -> 162 bytes .../__pycache__/__init__.cpython-313.pyc | Bin 0 -> 184 bytes gestion_fournisseur/models.py | 7 + .../details_fournisseur.html | 82 +++ .../templates/gestion_fournisseur/index.html | 64 ++ gestion_fournisseur/tests.py | 3 + gestion_fournisseur/urls.py | 33 + gestion_fournisseur/views.py | 195 ++++++ gestion_produit/__init__.py | 0 .../__pycache__/__init__.cpython-310.pyc | Bin 0 -> 147 bytes .../__pycache__/__init__.cpython-313.pyc | Bin 0 -> 169 bytes .../__pycache__/admin.cpython-310.pyc | Bin 0 -> 188 bytes .../__pycache__/admin.cpython-313.pyc | Bin 0 -> 207 bytes .../__pycache__/apps.cpython-310.pyc | Bin 0 -> 443 bytes .../__pycache__/apps.cpython-313.pyc | Bin 0 -> 544 bytes .../__pycache__/forms.cpython-310.pyc | Bin 0 -> 2819 bytes .../__pycache__/forms.cpython-313.pyc | Bin 0 -> 4069 bytes .../__pycache__/models.cpython-310.pyc | Bin 0 -> 4573 bytes .../__pycache__/models.cpython-313.pyc | Bin 0 -> 6765 bytes .../__pycache__/tests.cpython-313.pyc | Bin 0 -> 207 bytes .../__pycache__/urls.cpython-310.pyc | Bin 0 -> 1342 bytes .../__pycache__/urls.cpython-313.pyc | Bin 0 -> 1828 bytes .../__pycache__/views.cpython-310.pyc | Bin 0 -> 12476 bytes .../__pycache__/views.cpython-313.pyc | Bin 0 -> 17432 bytes gestion_produit/admin.py | 3 + gestion_produit/apps.py | 6 + gestion_produit/forms.py | 104 +++ gestion_produit/migrations/0001_initial.py | 78 +++ ..._alter_commander_date_commande_and_more.py | 29 + ..._alter_commander_date_commande_and_more.py | 24 + ..._alter_commander_date_commande_and_more.py | 24 + ..._alter_commander_date_commande_and_more.py | 24 + ..._alter_commander_date_commande_and_more.py | 24 + ..._alter_commander_date_commande_and_more.py | 24 + ..._alter_commander_date_commande_and_more.py | 24 + ..._alter_commander_date_commande_and_more.py | 24 + ..._alter_commander_date_commande_and_more.py | 24 + ..._alter_commander_date_commande_and_more.py | 24 + ..._alter_commander_date_commande_and_more.py | 29 + ..._alter_commander_date_commande_and_more.py | 24 + ..._alter_commander_date_commande_and_more.py | 36 + ...5_remove_produit_seuil_rupture_and_more.py | 33 + ..._alter_commander_date_commande_and_more.py | 24 + ..._alter_commander_date_commande_and_more.py | 24 + ..._alter_commander_date_commande_and_more.py | 24 + ..._alter_commander_date_commande_and_more.py | 24 + ..._alter_commander_date_commande_and_more.py | 24 + ..._alter_commander_date_commande_and_more.py | 34 + ...rnisseur_nifp_fournisseur_rccm_and_more.py | 34 + ..._alter_commander_date_commande_and_more.py | 29 + ..._alter_commander_date_commande_and_more.py | 54 ++ ...25_remove_demander_datedemande_and_more.py | 33 + ...ander_datedemiseadisposouhaite_and_more.py | 38 + ..._alter_commander_date_commande_and_more.py | 29 + gestion_produit/migrations/__init__.py | 0 .../__pycache__/0001_initial.cpython-310.pyc | Bin 0 -> 2869 bytes .../__pycache__/0001_initial.cpython-313.pyc | Bin 0 -> 5327 bytes ...der_date_commande_and_more.cpython-310.pyc | Bin 0 -> 871 bytes ...der_date_commande_and_more.cpython-313.pyc | Bin 0 -> 1395 bytes ...der_date_commande_and_more.cpython-313.pyc | Bin 0 -> 1420 bytes ...der_date_commande_and_more.cpython-310.pyc | Bin 0 -> 834 bytes ...der_date_commande_and_more.cpython-313.pyc | Bin 0 -> 1293 bytes ...der_date_commande_and_more.cpython-310.pyc | Bin 0 -> 839 bytes ...der_date_commande_and_more.cpython-313.pyc | Bin 0 -> 1298 bytes ..._valider_par_chef_and_more.cpython-313.pyc | Bin 0 -> 1769 bytes ...der_date_commande_and_more.cpython-310.pyc | Bin 0 -> 839 bytes ...der_date_commande_and_more.cpython-313.pyc | Bin 0 -> 1298 bytes ...der_date_commande_and_more.cpython-313.pyc | Bin 0 -> 1515 bytes ...der_date_commande_and_more.cpython-310.pyc | Bin 0 -> 834 bytes ...der_date_commande_and_more.cpython-313.pyc | Bin 0 -> 1288 bytes ...der_date_commande_and_more.cpython-313.pyc | Bin 0 -> 1498 bytes ...der_date_commande_and_more.cpython-310.pyc | Bin 0 -> 839 bytes ...der_date_commande_and_more.cpython-313.pyc | Bin 0 -> 1293 bytes ...der_date_commande_and_more.cpython-313.pyc | Bin 0 -> 1482 bytes ...der_date_commande_and_more.cpython-310.pyc | Bin 0 -> 839 bytes ...der_date_commande_and_more.cpython-313.pyc | Bin 0 -> 1293 bytes ...der_date_commande_and_more.cpython-310.pyc | Bin 0 -> 834 bytes ...der_date_commande_and_more.cpython-313.pyc | Bin 0 -> 1288 bytes ...der_date_commande_and_more.cpython-310.pyc | Bin 0 -> 839 bytes ...der_date_commande_and_more.cpython-313.pyc | Bin 0 -> 1298 bytes ...der_date_commande_and_more.cpython-310.pyc | Bin 0 -> 834 bytes ...der_date_commande_and_more.cpython-313.pyc | Bin 0 -> 1288 bytes ...der_date_commande_and_more.cpython-310.pyc | Bin 0 -> 922 bytes ...der_date_commande_and_more.cpython-313.pyc | Bin 0 -> 1451 bytes ...der_date_commande_and_more.cpython-310.pyc | Bin 0 -> 834 bytes ...der_date_commande_and_more.cpython-313.pyc | Bin 0 -> 1293 bytes ...der_date_commande_and_more.cpython-310.pyc | Bin 0 -> 1180 bytes ...der_date_commande_and_more.cpython-313.pyc | Bin 0 -> 1880 bytes ...uit_seuil_rupture_and_more.cpython-310.pyc | Bin 0 -> 1007 bytes ...uit_seuil_rupture_and_more.cpython-313.pyc | Bin 0 -> 1562 bytes ...der_date_commande_and_more.cpython-310.pyc | Bin 0 -> 833 bytes ...der_date_commande_and_more.cpython-313.pyc | Bin 0 -> 1292 bytes ...der_date_commande_and_more.cpython-310.pyc | Bin 0 -> 834 bytes ...der_date_commande_and_more.cpython-313.pyc | Bin 0 -> 1293 bytes ...der_date_commande_and_more.cpython-310.pyc | Bin 0 -> 839 bytes ...der_date_commande_and_more.cpython-313.pyc | Bin 0 -> 1298 bytes ...der_date_commande_and_more.cpython-310.pyc | Bin 0 -> 839 bytes ...der_date_commande_and_more.cpython-313.pyc | Bin 0 -> 1298 bytes ...der_date_commande_and_more.cpython-310.pyc | Bin 0 -> 839 bytes ...der_date_commande_and_more.cpython-313.pyc | Bin 0 -> 1298 bytes ...der_date_commande_and_more.cpython-310.pyc | Bin 0 -> 1062 bytes ...der_date_commande_and_more.cpython-313.pyc | Bin 0 -> 1659 bytes ..._fournisseur_rccm_and_more.cpython-310.pyc | Bin 0 -> 1117 bytes ..._fournisseur_rccm_and_more.cpython-313.pyc | Bin 0 -> 1733 bytes ...der_date_commande_and_more.cpython-310.pyc | Bin 0 -> 907 bytes ...der_date_commande_and_more.cpython-313.pyc | Bin 0 -> 1432 bytes ...der_date_commande_and_more.cpython-310.pyc | Bin 0 -> 1345 bytes ...der_date_commande_and_more.cpython-313.pyc | Bin 0 -> 2212 bytes ...ander_datedemande_and_more.cpython-310.pyc | Bin 0 -> 1065 bytes ...ander_datedemande_and_more.cpython-313.pyc | Bin 0 -> 1730 bytes ...iseadisposouhaite_and_more.cpython-310.pyc | Bin 0 -> 1169 bytes ...iseadisposouhaite_and_more.cpython-313.pyc | Bin 0 -> 1902 bytes ...der_date_commande_and_more.cpython-310.pyc | Bin 0 -> 933 bytes .../__pycache__/__init__.cpython-310.pyc | Bin 0 -> 158 bytes .../__pycache__/__init__.cpython-313.pyc | Bin 0 -> 180 bytes gestion_produit/models.py | 142 ++++ .../templates/gestion_produit/index.html | 325 +++++++++ .../gestion_produit/mouvement_stock.html | 28 + gestion_produit/tests.py | 3 + gestion_produit/urls.py | 70 ++ gestion_produit/views.py | 522 ++++++++++++++ gestion_vehicule/__init__.py | 0 .../__pycache__/__init__.cpython-310.pyc | Bin 0 -> 148 bytes .../__pycache__/__init__.cpython-313.pyc | Bin 0 -> 170 bytes .../__pycache__/admin.cpython-310.pyc | Bin 0 -> 189 bytes .../__pycache__/admin.cpython-313.pyc | Bin 0 -> 208 bytes .../__pycache__/apps.cpython-310.pyc | Bin 0 -> 446 bytes .../__pycache__/apps.cpython-313.pyc | Bin 0 -> 547 bytes .../__pycache__/forms.cpython-310.pyc | Bin 0 -> 2764 bytes .../__pycache__/forms.cpython-313.pyc | Bin 0 -> 4055 bytes .../__pycache__/models.cpython-310.pyc | Bin 0 -> 3872 bytes .../__pycache__/models.cpython-313.pyc | Bin 0 -> 5607 bytes .../__pycache__/tests.cpython-313.pyc | Bin 0 -> 208 bytes .../__pycache__/urls.cpython-310.pyc | Bin 0 -> 1843 bytes .../__pycache__/urls.cpython-313.pyc | Bin 0 -> 2432 bytes .../__pycache__/views.cpython-310.pyc | Bin 0 -> 16096 bytes .../__pycache__/views.cpython-313.pyc | Bin 0 -> 23511 bytes gestion_vehicule/admin.py | 3 + gestion_vehicule/apps.py | 6 + gestion_vehicule/forms.py | 105 +++ gestion_vehicule/migrations/0001_initial.py | 59 ++ ...ter_demandevehicule_date_heure_and_more.py | 24 + .../0003_alter_demandevehicule_validation.py | 18 + .../0004_demandevehicule_motif_refus.py | 18 + ...emandevehicule_course_terminer_and_more.py | 23 + ...tbord_id_alter_carnetbord_mois_concerne.py | 22 + .../0007_alter_carnetbord_km_fin_mois.py | 18 + ...0008_demandevehicule_chauffeur_and_more.py | 25 + ...emove_carnetbord_km_debut_mois_and_more.py | 69 ++ .../0010_carnetcarburant_course_and_more.py | 24 + .../0011_remove_carnetcarburant_vehicule.py | 17 + .../0012_alter_carnetbord_vehicule.py | 19 + ...013_alter_carnetbord_km_arrive_and_more.py | 38 + gestion_vehicule/migrations/__init__.py | 0 .../__pycache__/0001_initial.cpython-310.pyc | Bin 0 -> 2041 bytes .../__pycache__/0001_initial.cpython-313.pyc | Bin 0 -> 3572 bytes ...hicule_date_heure_and_more.cpython-310.pyc | Bin 0 -> 854 bytes ...hicule_date_heure_and_more.cpython-313.pyc | Bin 0 -> 1220 bytes ...demandevehicule_validation.cpython-310.pyc | Bin 0 -> 710 bytes ...demandevehicule_validation.cpython-313.pyc | Bin 0 -> 915 bytes ...emandevehicule_motif_refus.cpython-310.pyc | Bin 0 -> 671 bytes ...emandevehicule_motif_refus.cpython-313.pyc | Bin 0 -> 874 bytes ...e_course_terminer_and_more.cpython-310.pyc | Bin 0 -> 829 bytes ...e_course_terminer_and_more.cpython-313.pyc | Bin 0 -> 1105 bytes ...icule_heure_course_termine.cpython-313.pyc | Bin 0 -> 936 bytes ...r_carnetbord_mois_concerne.cpython-310.pyc | Bin 0 -> 781 bytes ...r_carnetbord_mois_concerne.cpython-313.pyc | Bin 0 -> 1020 bytes ...ter_carnetbord_km_fin_mois.cpython-310.pyc | Bin 0 -> 698 bytes ...ter_carnetbord_km_fin_mois.cpython-313.pyc | Bin 0 -> 903 bytes ...ehicule_chauffeur_and_more.cpython-310.pyc | Bin 0 -> 939 bytes ...ehicule_chauffeur_and_more.cpython-313.pyc | Bin 0 -> 1436 bytes ...ord_km_debut_mois_and_more.cpython-310.pyc | Bin 0 -> 1623 bytes ...ord_km_debut_mois_and_more.cpython-313.pyc | Bin 0 -> 2543 bytes ...tcarburant_course_and_more.cpython-310.pyc | Bin 0 -> 911 bytes ...tcarburant_course_and_more.cpython-313.pyc | Bin 0 -> 1287 bytes ...e_carnetcarburant_vehicule.cpython-310.pyc | Bin 0 -> 576 bytes ...e_carnetcarburant_vehicule.cpython-313.pyc | Bin 0 -> 744 bytes ..._alter_carnetbord_vehicule.cpython-310.pyc | Bin 0 -> 762 bytes ..._alter_carnetbord_vehicule.cpython-313.pyc | Bin 0 -> 1071 bytes ...netbord_km_arrive_and_more.cpython-310.pyc | Bin 0 -> 987 bytes ...netbord_km_arrive_and_more.cpython-313.pyc | Bin 0 -> 1461 bytes .../__pycache__/__init__.cpython-310.pyc | Bin 0 -> 159 bytes .../__pycache__/__init__.cpython-313.pyc | Bin 0 -> 181 bytes gestion_vehicule/models.py | 122 ++++ .../gestion_vehicule/carnet_carburant.html | 22 + .../carnet_sortie_vehicule.html | 22 + .../gestion_vehicule/detail_course.html | 131 ++++ .../gestion_vehicule/detail_vehicule.html | 79 +++ .../templates/gestion_vehicule/index.html | 202 ++++++ gestion_vehicule/tests.py | 3 + gestion_vehicule/urls.py | 88 +++ gestion_vehicule/views.py | 648 ++++++++++++++++++ manage.py | 23 + .../nifp/Equipe_3_Fria_centre_Menage.pdf | Bin 0 -> 230843 bytes .../nifp/RAPPORT_DANALYSE_DU_10.12.2024.pdf | Bin 0 -> 174407 bytes .../Programme-Master-Finance-Digitale-DIT.pdf | Bin 0 -> 152445 bytes .../rccm/RAPPORT_DANALYSE_DU_10.12.2024.pdf | Bin 0 -> 174407 bytes .../LOGO_AFRICAM_PREACTS_GUINEE_FR.jpg | Bin 0 -> 561974 bytes ...LOGO_AFRICAM_PREACTS_GUINEE_FR_RKxGJa0.jpg | Bin 0 -> 561974 bytes ...LOGO_AFRICAM_PREACTS_GUINEE_FR_k6t6gJ7.jpg | Bin 0 -> 561974 bytes ...LOGO_AFRICAM_PREACTS_GUINEE_FR_nGBZs9l.jpg | Bin 0 -> 561974 bytes ...LOGO_AFRICAM_PREACTS_GUINEE_FR_ngW1veO.jpg | Bin 0 -> 561974 bytes media/produit_image/Rplot.png | Bin 0 -> 6137 bytes media/produit_image/bilan_exploration.png | Bin 0 -> 19331 bytes ...le-de-rapport-lien-pdf-laboratoire-mgd.jpg | Bin 0 -> 54295 bytes ...pport-lien-pdf-laboratoire-mgd_9idXmSP.jpg | Bin 0 -> 54295 bytes ...pport-lien-pdf-laboratoire-mgd_Pa9vHK7.jpg | Bin 0 -> 54295 bytes ...pport-lien-pdf-laboratoire-mgd_qrNf5vF.jpg | Bin 0 -> 54295 bytes media/produit_image/logo.ico | Bin 0 -> 111998 bytes media/produit_image/logo.jpg | Bin 0 -> 21929 bytes media/produit_image/logo_3Ufp6I9.jpg | Bin 0 -> 21929 bytes media/produit_image/logo_8sK9e1R.jpg | Bin 0 -> 21929 bytes media/produit_image/logo_KeooBek.ico | Bin 0 -> 111998 bytes media/produit_image/logo_cmYUgKP.jpg | Bin 0 -> 21929 bytes media/produit_image/logo_doq5TsE.jpg | Bin 0 -> 21929 bytes media/produit_image/logo_fHPzfwp.ico | Bin 0 -> 111998 bytes media/produit_image/téléchargement.jpg | Bin 0 -> 8660 bytes .../produit_image/téléchargement_11nr3Zb.jpg | Bin 0 -> 8660 bytes .../produit_image/téléchargement_BmsEqGY.jpg | Bin 0 -> 8660 bytes .../produit_image/téléchargement_EwmRaDh.jpg | Bin 0 -> 8660 bytes media/vehicule_image/logo.ico | Bin 0 -> 111998 bytes media/vehicule_image/téléchargement.jpg | Bin 0 -> 8660 bytes .../vehicule_image/téléchargement_0am1A2J.jpg | Bin 0 -> 8660 bytes .../vehicule_image/téléchargement_6pPxAX4.jpg | Bin 0 -> 8660 bytes .../vehicule_image/téléchargement_8FFpOHu.jpg | Bin 0 -> 8660 bytes .../vehicule_image/téléchargement_LpXAquO.jpg | Bin 0 -> 8660 bytes .../vehicule_image/téléchargement_VsOO72y.jpg | Bin 0 -> 8660 bytes .../vehicule_image/téléchargement_Z9fTDJk.jpg | Bin 0 -> 8660 bytes .../vehicule_image/téléchargement_h9sCIg4.jpg | Bin 0 -> 8660 bytes .../vehicule_image/téléchargement_kTZyDoZ.jpg | Bin 0 -> 8660 bytes .../vehicule_image/téléchargement_nbQMCJB.jpg | Bin 0 -> 8660 bytes .../vehicule_image/téléchargement_yp1otbv.jpg | Bin 0 -> 8660 bytes pyproject.toml | 34 + requirements.txt | Bin 0 -> 200 bytes static/css/base.css | 0 static/css/bootstrap.min.css | 6 + static/css/cadran_image.css | 0 static/css/tabulator_bootstrap5.min.css | 2 + static/images/exemple-produit.jpg | Bin 0 -> 7263 bytes static/images/stock-bon.png | Bin 0 -> 9810 bytes static/images/stock-prerupture.png | Bin 0 -> 10754 bytes static/images/stock-rupture.png | Bin 0 -> 6136 bytes static/js/Untitled-1.py | 14 + static/js/bootstrap.min.js | 7 + static/js/carnet_carburant.js | 25 + static/js/carnet_sortie_vehicule.js | 23 + static/js/detail_course.js | 9 + static/js/detail_gestion_vehicule.js | 24 + static/js/details_fournisseur.js | 24 + static/js/gestion_fournisseur_index.js | 34 + static/js/gestion_produit.js | 231 +++++++ static/js/gestion_vehicule.js | 166 +++++ static/js/index.js | 197 ++++++ static/js/mouvement_stock.js | 52 ++ static/js/tabulator.min.js | 3 + 336 files changed, 6247 insertions(+) create mode 100644 .gitignore create mode 100644 SGL/__init__.py create mode 100644 SGL/__pycache__/__init__.cpython-310.pyc create mode 100644 SGL/__pycache__/__init__.cpython-313.pyc create mode 100644 SGL/__pycache__/settings.cpython-310.pyc create mode 100644 SGL/__pycache__/settings.cpython-313.pyc create mode 100644 SGL/__pycache__/urls.cpython-310.pyc create mode 100644 SGL/__pycache__/urls.cpython-313.pyc create mode 100644 SGL/__pycache__/views.cpython-310.pyc create mode 100644 SGL/__pycache__/views.cpython-313.pyc create mode 100644 SGL/__pycache__/wsgi.cpython-310.pyc create mode 100644 SGL/__pycache__/wsgi.cpython-313.pyc create mode 100644 SGL/asgi.py create mode 100644 SGL/settings.py create mode 100644 SGL/templates/BASE.html create mode 100644 SGL/templates/emails/email_template.html create mode 100644 SGL/templates/emails/téléchargement.png create mode 100644 SGL/templates/emails/téléchargement.png:Zone.Identifier create mode 100644 SGL/templates/index.html create mode 100644 SGL/urls.py create mode 100644 SGL/views.py create mode 100644 SGL/wsgi.py create mode 100644 authentification/__init__.py create mode 100644 authentification/__pycache__/__init__.cpython-310.pyc create mode 100644 authentification/__pycache__/__init__.cpython-313.pyc create mode 100644 authentification/__pycache__/admin.cpython-310.pyc create mode 100644 authentification/__pycache__/admin.cpython-313.pyc create mode 100644 authentification/__pycache__/apps.cpython-310.pyc create mode 100644 authentification/__pycache__/apps.cpython-313.pyc create mode 100644 authentification/__pycache__/models.cpython-310.pyc create mode 100644 authentification/__pycache__/models.cpython-313.pyc create mode 100644 authentification/__pycache__/tests.cpython-313.pyc create mode 100644 authentification/__pycache__/urls.cpython-310.pyc create mode 100644 authentification/__pycache__/urls.cpython-313.pyc create mode 100644 authentification/__pycache__/views.cpython-310.pyc create mode 100644 authentification/__pycache__/views.cpython-313.pyc create mode 100644 authentification/admin.py create mode 100644 authentification/apps.py create mode 100644 authentification/migrations/0001_initial.py create mode 100644 authentification/migrations/__init__.py create mode 100644 authentification/migrations/__pycache__/0001_initial.cpython-310.pyc create mode 100644 authentification/migrations/__pycache__/0001_initial.cpython-313.pyc create mode 100644 authentification/migrations/__pycache__/__init__.cpython-310.pyc create mode 100644 authentification/migrations/__pycache__/__init__.cpython-313.pyc create mode 100644 authentification/models.py create mode 100644 authentification/templates/authentification/login.html create mode 100644 authentification/templatetags/__init__.py create mode 100644 authentification/templatetags/__pycache__/__init__.cpython-310.pyc create mode 100644 authentification/templatetags/__pycache__/__init__.cpython-313.pyc create mode 100644 authentification/templatetags/__pycache__/group_tags.cpython-313.pyc create mode 100644 authentification/templatetags/__pycache__/sorel.cpython-313.pyc create mode 100644 authentification/templatetags/__pycache__/tags_personnaliser.cpython-310.pyc create mode 100644 authentification/templatetags/__pycache__/tags_personnaliser.cpython-313.pyc create mode 100644 authentification/templatetags/tags_personnaliser.py create mode 100644 authentification/tests.py create mode 100644 authentification/urls.py create mode 100644 authentification/views.py create mode 100644 gestion_fournisseur/__init__.py create mode 100644 gestion_fournisseur/__pycache__/__init__.cpython-310.pyc create mode 100644 gestion_fournisseur/__pycache__/__init__.cpython-313.pyc create mode 100644 gestion_fournisseur/__pycache__/admin.cpython-310.pyc create mode 100644 gestion_fournisseur/__pycache__/admin.cpython-313.pyc create mode 100644 gestion_fournisseur/__pycache__/apps.cpython-310.pyc create mode 100644 gestion_fournisseur/__pycache__/apps.cpython-313.pyc create mode 100644 gestion_fournisseur/__pycache__/forms.cpython-310.pyc create mode 100644 gestion_fournisseur/__pycache__/forms.cpython-313.pyc create mode 100644 gestion_fournisseur/__pycache__/models.cpython-310.pyc create mode 100644 gestion_fournisseur/__pycache__/models.cpython-313.pyc create mode 100644 gestion_fournisseur/__pycache__/tests.cpython-313.pyc create mode 100644 gestion_fournisseur/__pycache__/urls.cpython-310.pyc create mode 100644 gestion_fournisseur/__pycache__/urls.cpython-313.pyc create mode 100644 gestion_fournisseur/__pycache__/views.cpython-310.pyc create mode 100644 gestion_fournisseur/__pycache__/views.cpython-313.pyc create mode 100644 gestion_fournisseur/admin.py create mode 100644 gestion_fournisseur/apps.py create mode 100644 gestion_fournisseur/forms.py create mode 100644 gestion_fournisseur/migrations/__init__.py create mode 100644 gestion_fournisseur/migrations/__pycache__/0001_initial.cpython-313.pyc create mode 100644 gestion_fournisseur/migrations/__pycache__/0002_alter_fournisseur_categorie_alter_fournisseur_email_and_more.cpython-313.pyc create mode 100644 gestion_fournisseur/migrations/__pycache__/0002_remove_fournisseur_categorie_fournisseur_categorie.cpython-313.pyc create mode 100644 gestion_fournisseur/migrations/__pycache__/0003_alter_fournisseur_telephone.cpython-313.pyc create mode 100644 gestion_fournisseur/migrations/__pycache__/__init__.cpython-310.pyc create mode 100644 gestion_fournisseur/migrations/__pycache__/__init__.cpython-313.pyc create mode 100644 gestion_fournisseur/models.py create mode 100644 gestion_fournisseur/templates/gestion_fournisseur/details_fournisseur.html create mode 100644 gestion_fournisseur/templates/gestion_fournisseur/index.html create mode 100644 gestion_fournisseur/tests.py create mode 100644 gestion_fournisseur/urls.py create mode 100644 gestion_fournisseur/views.py create mode 100644 gestion_produit/__init__.py create mode 100644 gestion_produit/__pycache__/__init__.cpython-310.pyc create mode 100644 gestion_produit/__pycache__/__init__.cpython-313.pyc create mode 100644 gestion_produit/__pycache__/admin.cpython-310.pyc create mode 100644 gestion_produit/__pycache__/admin.cpython-313.pyc create mode 100644 gestion_produit/__pycache__/apps.cpython-310.pyc create mode 100644 gestion_produit/__pycache__/apps.cpython-313.pyc create mode 100644 gestion_produit/__pycache__/forms.cpython-310.pyc create mode 100644 gestion_produit/__pycache__/forms.cpython-313.pyc create mode 100644 gestion_produit/__pycache__/models.cpython-310.pyc create mode 100644 gestion_produit/__pycache__/models.cpython-313.pyc create mode 100644 gestion_produit/__pycache__/tests.cpython-313.pyc create mode 100644 gestion_produit/__pycache__/urls.cpython-310.pyc create mode 100644 gestion_produit/__pycache__/urls.cpython-313.pyc create mode 100644 gestion_produit/__pycache__/views.cpython-310.pyc create mode 100644 gestion_produit/__pycache__/views.cpython-313.pyc create mode 100644 gestion_produit/admin.py create mode 100644 gestion_produit/apps.py create mode 100644 gestion_produit/forms.py create mode 100644 gestion_produit/migrations/0001_initial.py create mode 100644 gestion_produit/migrations/0002_alter_commander_date_commande_and_more.py create mode 100644 gestion_produit/migrations/0003_alter_commander_date_commande_and_more.py create mode 100644 gestion_produit/migrations/0004_alter_commander_date_commande_and_more.py create mode 100644 gestion_produit/migrations/0005_alter_commander_date_commande_and_more.py create mode 100644 gestion_produit/migrations/0006_alter_commander_date_commande_and_more.py create mode 100644 gestion_produit/migrations/0007_alter_commander_date_commande_and_more.py create mode 100644 gestion_produit/migrations/0008_alter_commander_date_commande_and_more.py create mode 100644 gestion_produit/migrations/0009_alter_commander_date_commande_and_more.py create mode 100644 gestion_produit/migrations/0010_alter_commander_date_commande_and_more.py create mode 100644 gestion_produit/migrations/0011_alter_commander_date_commande_and_more.py create mode 100644 gestion_produit/migrations/0012_alter_commander_date_commande_and_more.py create mode 100644 gestion_produit/migrations/0013_alter_commander_date_commande_and_more.py create mode 100644 gestion_produit/migrations/0014_demander_user_alter_commander_date_commande_and_more.py create mode 100644 gestion_produit/migrations/0015_remove_produit_seuil_rupture_and_more.py create mode 100644 gestion_produit/migrations/0016_alter_commander_date_commande_and_more.py create mode 100644 gestion_produit/migrations/0017_alter_commander_date_commande_and_more.py create mode 100644 gestion_produit/migrations/0018_alter_commander_date_commande_and_more.py create mode 100644 gestion_produit/migrations/0019_alter_commander_date_commande_and_more.py create mode 100644 gestion_produit/migrations/0020_alter_commander_date_commande_and_more.py create mode 100644 gestion_produit/migrations/0021_commander_prix_achat_alter_commander_date_commande_and_more.py create mode 100644 gestion_produit/migrations/0022_fournisseur_nifp_fournisseur_rccm_and_more.py create mode 100644 gestion_produit/migrations/0023_alter_commander_date_commande_and_more.py create mode 100644 gestion_produit/migrations/0024_alter_commander_date_commande_and_more.py create mode 100644 gestion_produit/migrations/0025_remove_demander_datedemande_and_more.py create mode 100644 gestion_produit/migrations/0026_remove_demander_datedemiseadisposouhaite_and_more.py create mode 100644 gestion_produit/migrations/0027_alter_commander_date_commande_and_more.py create mode 100644 gestion_produit/migrations/__init__.py create mode 100644 gestion_produit/migrations/__pycache__/0001_initial.cpython-310.pyc create mode 100644 gestion_produit/migrations/__pycache__/0001_initial.cpython-313.pyc create mode 100644 gestion_produit/migrations/__pycache__/0002_alter_commander_date_commande_and_more.cpython-310.pyc create mode 100644 gestion_produit/migrations/__pycache__/0002_alter_commander_date_commande_and_more.cpython-313.pyc create mode 100644 gestion_produit/migrations/__pycache__/0002_commander_livrer_alter_commander_date_commande_and_more.cpython-313.pyc create mode 100644 gestion_produit/migrations/__pycache__/0003_alter_commander_date_commande_and_more.cpython-310.pyc create mode 100644 gestion_produit/migrations/__pycache__/0003_alter_commander_date_commande_and_more.cpython-313.pyc create mode 100644 gestion_produit/migrations/__pycache__/0004_alter_commander_date_commande_and_more.cpython-310.pyc create mode 100644 gestion_produit/migrations/__pycache__/0004_alter_commander_date_commande_and_more.cpython-313.pyc create mode 100644 gestion_produit/migrations/__pycache__/0004_demander_valider_par_chef_and_more.cpython-313.pyc create mode 100644 gestion_produit/migrations/__pycache__/0005_alter_commander_date_commande_and_more.cpython-310.pyc create mode 100644 gestion_produit/migrations/__pycache__/0005_alter_commander_date_commande_and_more.cpython-313.pyc create mode 100644 gestion_produit/migrations/__pycache__/0005_demander_quantite_alter_commander_date_commande_and_more.cpython-313.pyc create mode 100644 gestion_produit/migrations/__pycache__/0006_alter_commander_date_commande_and_more.cpython-310.pyc create mode 100644 gestion_produit/migrations/__pycache__/0006_alter_commander_date_commande_and_more.cpython-313.pyc create mode 100644 gestion_produit/migrations/__pycache__/0006_demander_motif_refus_alter_commander_date_commande_and_more.cpython-313.pyc create mode 100644 gestion_produit/migrations/__pycache__/0007_alter_commander_date_commande_and_more.cpython-310.pyc create mode 100644 gestion_produit/migrations/__pycache__/0007_alter_commander_date_commande_and_more.cpython-313.pyc create mode 100644 gestion_produit/migrations/__pycache__/0007_demander_livrer_alter_commander_date_commande_and_more.cpython-313.pyc create mode 100644 gestion_produit/migrations/__pycache__/0008_alter_commander_date_commande_and_more.cpython-310.pyc create mode 100644 gestion_produit/migrations/__pycache__/0008_alter_commander_date_commande_and_more.cpython-313.pyc create mode 100644 gestion_produit/migrations/__pycache__/0009_alter_commander_date_commande_and_more.cpython-310.pyc create mode 100644 gestion_produit/migrations/__pycache__/0009_alter_commander_date_commande_and_more.cpython-313.pyc create mode 100644 gestion_produit/migrations/__pycache__/0010_alter_commander_date_commande_and_more.cpython-310.pyc create mode 100644 gestion_produit/migrations/__pycache__/0010_alter_commander_date_commande_and_more.cpython-313.pyc create mode 100644 gestion_produit/migrations/__pycache__/0011_alter_commander_date_commande_and_more.cpython-310.pyc create mode 100644 gestion_produit/migrations/__pycache__/0011_alter_commander_date_commande_and_more.cpython-313.pyc create mode 100644 gestion_produit/migrations/__pycache__/0012_alter_commander_date_commande_and_more.cpython-310.pyc create mode 100644 gestion_produit/migrations/__pycache__/0012_alter_commander_date_commande_and_more.cpython-313.pyc create mode 100644 gestion_produit/migrations/__pycache__/0013_alter_commander_date_commande_and_more.cpython-310.pyc create mode 100644 gestion_produit/migrations/__pycache__/0013_alter_commander_date_commande_and_more.cpython-313.pyc create mode 100644 gestion_produit/migrations/__pycache__/0014_demander_user_alter_commander_date_commande_and_more.cpython-310.pyc create mode 100644 gestion_produit/migrations/__pycache__/0014_demander_user_alter_commander_date_commande_and_more.cpython-313.pyc create mode 100644 gestion_produit/migrations/__pycache__/0015_remove_produit_seuil_rupture_and_more.cpython-310.pyc create mode 100644 gestion_produit/migrations/__pycache__/0015_remove_produit_seuil_rupture_and_more.cpython-313.pyc create mode 100644 gestion_produit/migrations/__pycache__/0016_alter_commander_date_commande_and_more.cpython-310.pyc create mode 100644 gestion_produit/migrations/__pycache__/0016_alter_commander_date_commande_and_more.cpython-313.pyc create mode 100644 gestion_produit/migrations/__pycache__/0017_alter_commander_date_commande_and_more.cpython-310.pyc create mode 100644 gestion_produit/migrations/__pycache__/0017_alter_commander_date_commande_and_more.cpython-313.pyc create mode 100644 gestion_produit/migrations/__pycache__/0018_alter_commander_date_commande_and_more.cpython-310.pyc create mode 100644 gestion_produit/migrations/__pycache__/0018_alter_commander_date_commande_and_more.cpython-313.pyc create mode 100644 gestion_produit/migrations/__pycache__/0019_alter_commander_date_commande_and_more.cpython-310.pyc create mode 100644 gestion_produit/migrations/__pycache__/0019_alter_commander_date_commande_and_more.cpython-313.pyc create mode 100644 gestion_produit/migrations/__pycache__/0020_alter_commander_date_commande_and_more.cpython-310.pyc create mode 100644 gestion_produit/migrations/__pycache__/0020_alter_commander_date_commande_and_more.cpython-313.pyc create mode 100644 gestion_produit/migrations/__pycache__/0021_commander_prix_achat_alter_commander_date_commande_and_more.cpython-310.pyc create mode 100644 gestion_produit/migrations/__pycache__/0021_commander_prix_achat_alter_commander_date_commande_and_more.cpython-313.pyc create mode 100644 gestion_produit/migrations/__pycache__/0022_fournisseur_nifp_fournisseur_rccm_and_more.cpython-310.pyc create mode 100644 gestion_produit/migrations/__pycache__/0022_fournisseur_nifp_fournisseur_rccm_and_more.cpython-313.pyc create mode 100644 gestion_produit/migrations/__pycache__/0023_alter_commander_date_commande_and_more.cpython-310.pyc create mode 100644 gestion_produit/migrations/__pycache__/0023_alter_commander_date_commande_and_more.cpython-313.pyc create mode 100644 gestion_produit/migrations/__pycache__/0024_alter_commander_date_commande_and_more.cpython-310.pyc create mode 100644 gestion_produit/migrations/__pycache__/0024_alter_commander_date_commande_and_more.cpython-313.pyc create mode 100644 gestion_produit/migrations/__pycache__/0025_remove_demander_datedemande_and_more.cpython-310.pyc create mode 100644 gestion_produit/migrations/__pycache__/0025_remove_demander_datedemande_and_more.cpython-313.pyc create mode 100644 gestion_produit/migrations/__pycache__/0026_remove_demander_datedemiseadisposouhaite_and_more.cpython-310.pyc create mode 100644 gestion_produit/migrations/__pycache__/0026_remove_demander_datedemiseadisposouhaite_and_more.cpython-313.pyc create mode 100644 gestion_produit/migrations/__pycache__/0027_alter_commander_date_commande_and_more.cpython-310.pyc create mode 100644 gestion_produit/migrations/__pycache__/__init__.cpython-310.pyc create mode 100644 gestion_produit/migrations/__pycache__/__init__.cpython-313.pyc create mode 100644 gestion_produit/models.py create mode 100644 gestion_produit/templates/gestion_produit/index.html create mode 100644 gestion_produit/templates/gestion_produit/mouvement_stock.html create mode 100644 gestion_produit/tests.py create mode 100644 gestion_produit/urls.py create mode 100644 gestion_produit/views.py create mode 100644 gestion_vehicule/__init__.py create mode 100644 gestion_vehicule/__pycache__/__init__.cpython-310.pyc create mode 100644 gestion_vehicule/__pycache__/__init__.cpython-313.pyc create mode 100644 gestion_vehicule/__pycache__/admin.cpython-310.pyc create mode 100644 gestion_vehicule/__pycache__/admin.cpython-313.pyc create mode 100644 gestion_vehicule/__pycache__/apps.cpython-310.pyc create mode 100644 gestion_vehicule/__pycache__/apps.cpython-313.pyc create mode 100644 gestion_vehicule/__pycache__/forms.cpython-310.pyc create mode 100644 gestion_vehicule/__pycache__/forms.cpython-313.pyc create mode 100644 gestion_vehicule/__pycache__/models.cpython-310.pyc create mode 100644 gestion_vehicule/__pycache__/models.cpython-313.pyc create mode 100644 gestion_vehicule/__pycache__/tests.cpython-313.pyc create mode 100644 gestion_vehicule/__pycache__/urls.cpython-310.pyc create mode 100644 gestion_vehicule/__pycache__/urls.cpython-313.pyc create mode 100644 gestion_vehicule/__pycache__/views.cpython-310.pyc create mode 100644 gestion_vehicule/__pycache__/views.cpython-313.pyc create mode 100644 gestion_vehicule/admin.py create mode 100644 gestion_vehicule/apps.py create mode 100644 gestion_vehicule/forms.py create mode 100644 gestion_vehicule/migrations/0001_initial.py create mode 100644 gestion_vehicule/migrations/0002_alter_demandevehicule_date_heure_and_more.py create mode 100644 gestion_vehicule/migrations/0003_alter_demandevehicule_validation.py create mode 100644 gestion_vehicule/migrations/0004_demandevehicule_motif_refus.py create mode 100644 gestion_vehicule/migrations/0005_demandevehicule_course_terminer_and_more.py create mode 100644 gestion_vehicule/migrations/0006_remove_carnetbord_id_alter_carnetbord_mois_concerne.py create mode 100644 gestion_vehicule/migrations/0007_alter_carnetbord_km_fin_mois.py create mode 100644 gestion_vehicule/migrations/0008_demandevehicule_chauffeur_and_more.py create mode 100644 gestion_vehicule/migrations/0009_remove_carnetbord_km_debut_mois_and_more.py create mode 100644 gestion_vehicule/migrations/0010_carnetcarburant_course_and_more.py create mode 100644 gestion_vehicule/migrations/0011_remove_carnetcarburant_vehicule.py create mode 100644 gestion_vehicule/migrations/0012_alter_carnetbord_vehicule.py create mode 100644 gestion_vehicule/migrations/0013_alter_carnetbord_km_arrive_and_more.py create mode 100644 gestion_vehicule/migrations/__init__.py create mode 100644 gestion_vehicule/migrations/__pycache__/0001_initial.cpython-310.pyc create mode 100644 gestion_vehicule/migrations/__pycache__/0001_initial.cpython-313.pyc create mode 100644 gestion_vehicule/migrations/__pycache__/0002_alter_demandevehicule_date_heure_and_more.cpython-310.pyc create mode 100644 gestion_vehicule/migrations/__pycache__/0002_alter_demandevehicule_date_heure_and_more.cpython-313.pyc create mode 100644 gestion_vehicule/migrations/__pycache__/0003_alter_demandevehicule_validation.cpython-310.pyc create mode 100644 gestion_vehicule/migrations/__pycache__/0003_alter_demandevehicule_validation.cpython-313.pyc create mode 100644 gestion_vehicule/migrations/__pycache__/0004_demandevehicule_motif_refus.cpython-310.pyc create mode 100644 gestion_vehicule/migrations/__pycache__/0004_demandevehicule_motif_refus.cpython-313.pyc create mode 100644 gestion_vehicule/migrations/__pycache__/0005_demandevehicule_course_terminer_and_more.cpython-310.pyc create mode 100644 gestion_vehicule/migrations/__pycache__/0005_demandevehicule_course_terminer_and_more.cpython-313.pyc create mode 100644 gestion_vehicule/migrations/__pycache__/0006_alter_demandevehicule_heure_course_termine.cpython-313.pyc create mode 100644 gestion_vehicule/migrations/__pycache__/0006_remove_carnetbord_id_alter_carnetbord_mois_concerne.cpython-310.pyc create mode 100644 gestion_vehicule/migrations/__pycache__/0006_remove_carnetbord_id_alter_carnetbord_mois_concerne.cpython-313.pyc create mode 100644 gestion_vehicule/migrations/__pycache__/0007_alter_carnetbord_km_fin_mois.cpython-310.pyc create mode 100644 gestion_vehicule/migrations/__pycache__/0007_alter_carnetbord_km_fin_mois.cpython-313.pyc create mode 100644 gestion_vehicule/migrations/__pycache__/0008_demandevehicule_chauffeur_and_more.cpython-310.pyc create mode 100644 gestion_vehicule/migrations/__pycache__/0008_demandevehicule_chauffeur_and_more.cpython-313.pyc create mode 100644 gestion_vehicule/migrations/__pycache__/0009_remove_carnetbord_km_debut_mois_and_more.cpython-310.pyc create mode 100644 gestion_vehicule/migrations/__pycache__/0009_remove_carnetbord_km_debut_mois_and_more.cpython-313.pyc create mode 100644 gestion_vehicule/migrations/__pycache__/0010_carnetcarburant_course_and_more.cpython-310.pyc create mode 100644 gestion_vehicule/migrations/__pycache__/0010_carnetcarburant_course_and_more.cpython-313.pyc create mode 100644 gestion_vehicule/migrations/__pycache__/0011_remove_carnetcarburant_vehicule.cpython-310.pyc create mode 100644 gestion_vehicule/migrations/__pycache__/0011_remove_carnetcarburant_vehicule.cpython-313.pyc create mode 100644 gestion_vehicule/migrations/__pycache__/0012_alter_carnetbord_vehicule.cpython-310.pyc create mode 100644 gestion_vehicule/migrations/__pycache__/0012_alter_carnetbord_vehicule.cpython-313.pyc create mode 100644 gestion_vehicule/migrations/__pycache__/0013_alter_carnetbord_km_arrive_and_more.cpython-310.pyc create mode 100644 gestion_vehicule/migrations/__pycache__/0013_alter_carnetbord_km_arrive_and_more.cpython-313.pyc create mode 100644 gestion_vehicule/migrations/__pycache__/__init__.cpython-310.pyc create mode 100644 gestion_vehicule/migrations/__pycache__/__init__.cpython-313.pyc create mode 100644 gestion_vehicule/models.py create mode 100644 gestion_vehicule/templates/gestion_vehicule/carnet_carburant.html create mode 100644 gestion_vehicule/templates/gestion_vehicule/carnet_sortie_vehicule.html create mode 100644 gestion_vehicule/templates/gestion_vehicule/detail_course.html create mode 100644 gestion_vehicule/templates/gestion_vehicule/detail_vehicule.html create mode 100644 gestion_vehicule/templates/gestion_vehicule/index.html create mode 100644 gestion_vehicule/tests.py create mode 100644 gestion_vehicule/urls.py create mode 100644 gestion_vehicule/views.py create mode 100644 manage.py create mode 100644 media/fournisseur/nifp/Equipe_3_Fria_centre_Menage.pdf create mode 100644 media/fournisseur/nifp/RAPPORT_DANALYSE_DU_10.12.2024.pdf create mode 100644 media/fournisseur/rccm/Programme-Master-Finance-Digitale-DIT.pdf create mode 100644 media/fournisseur/rccm/RAPPORT_DANALYSE_DU_10.12.2024.pdf create mode 100644 media/produit_image/LOGO_AFRICAM_PREACTS_GUINEE_FR.jpg create mode 100644 media/produit_image/LOGO_AFRICAM_PREACTS_GUINEE_FR_RKxGJa0.jpg create mode 100644 media/produit_image/LOGO_AFRICAM_PREACTS_GUINEE_FR_k6t6gJ7.jpg create mode 100644 media/produit_image/LOGO_AFRICAM_PREACTS_GUINEE_FR_nGBZs9l.jpg create mode 100644 media/produit_image/LOGO_AFRICAM_PREACTS_GUINEE_FR_ngW1veO.jpg create mode 100644 media/produit_image/Rplot.png create mode 100644 media/produit_image/bilan_exploration.png create mode 100644 media/produit_image/exemple-de-rapport-lien-pdf-laboratoire-mgd.jpg create mode 100644 media/produit_image/exemple-de-rapport-lien-pdf-laboratoire-mgd_9idXmSP.jpg create mode 100644 media/produit_image/exemple-de-rapport-lien-pdf-laboratoire-mgd_Pa9vHK7.jpg create mode 100644 media/produit_image/exemple-de-rapport-lien-pdf-laboratoire-mgd_qrNf5vF.jpg create mode 100644 media/produit_image/logo.ico create mode 100644 media/produit_image/logo.jpg create mode 100644 media/produit_image/logo_3Ufp6I9.jpg create mode 100644 media/produit_image/logo_8sK9e1R.jpg create mode 100644 media/produit_image/logo_KeooBek.ico create mode 100644 media/produit_image/logo_cmYUgKP.jpg create mode 100644 media/produit_image/logo_doq5TsE.jpg create mode 100644 media/produit_image/logo_fHPzfwp.ico create mode 100644 media/produit_image/téléchargement.jpg create mode 100644 media/produit_image/téléchargement_11nr3Zb.jpg create mode 100644 media/produit_image/téléchargement_BmsEqGY.jpg create mode 100644 media/produit_image/téléchargement_EwmRaDh.jpg create mode 100644 media/vehicule_image/logo.ico create mode 100644 media/vehicule_image/téléchargement.jpg create mode 100644 media/vehicule_image/téléchargement_0am1A2J.jpg create mode 100644 media/vehicule_image/téléchargement_6pPxAX4.jpg create mode 100644 media/vehicule_image/téléchargement_8FFpOHu.jpg create mode 100644 media/vehicule_image/téléchargement_LpXAquO.jpg create mode 100644 media/vehicule_image/téléchargement_VsOO72y.jpg create mode 100644 media/vehicule_image/téléchargement_Z9fTDJk.jpg create mode 100644 media/vehicule_image/téléchargement_h9sCIg4.jpg create mode 100644 media/vehicule_image/téléchargement_kTZyDoZ.jpg create mode 100644 media/vehicule_image/téléchargement_nbQMCJB.jpg create mode 100644 media/vehicule_image/téléchargement_yp1otbv.jpg create mode 100644 pyproject.toml create mode 100644 requirements.txt create mode 100644 static/css/base.css create mode 100644 static/css/bootstrap.min.css create mode 100644 static/css/cadran_image.css create mode 100644 static/css/tabulator_bootstrap5.min.css create mode 100644 static/images/exemple-produit.jpg create mode 100644 static/images/stock-bon.png create mode 100644 static/images/stock-prerupture.png create mode 100644 static/images/stock-rupture.png create mode 100644 static/js/Untitled-1.py create mode 100644 static/js/bootstrap.min.js create mode 100644 static/js/carnet_carburant.js create mode 100644 static/js/carnet_sortie_vehicule.js create mode 100644 static/js/detail_course.js create mode 100644 static/js/detail_gestion_vehicule.js create mode 100644 static/js/details_fournisseur.js create mode 100644 static/js/gestion_fournisseur_index.js create mode 100644 static/js/gestion_produit.js create mode 100644 static/js/gestion_vehicule.js create mode 100644 static/js/index.js create mode 100644 static/js/mouvement_stock.js create mode 100644 static/js/tabulator.min.js diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..d962d96 --- /dev/null +++ b/.gitignore @@ -0,0 +1,3 @@ +.ruff_cache/ +.coverage +db.sqlite3 \ No newline at end of file diff --git a/SGL/__init__.py b/SGL/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/SGL/__pycache__/__init__.cpython-310.pyc b/SGL/__pycache__/__init__.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..08bb9acb58b48acd0dfb3e9c9c09031c4cc930b1 GIT binary patch literal 135 zcmd1j<>g`k01DR3G1SD7(00>$f A4gdfE literal 0 HcmV?d00001 diff --git a/SGL/__pycache__/__init__.cpython-313.pyc b/SGL/__pycache__/__init__.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..bcbf16dc4e4af0c98c606181c52532370f3596e9 GIT binary patch literal 157 zcmey&%ge<81YAq6Wq|0%AOZ#$p^VQgK*m&tbOudEzm*I{OhDdekkl<3XRDad;?$zz zm=OQaAXkL|=NOmN;_QvNwyP@VW!mbu0DPHyqL?i@F(W31aNLeNk|Bu#j^UYi;;)I{gkG|jG*U=1X3>n1?g+-Ij(`#$ zL}L!_Nw{ZF$~cW?v4m47jZVFbcSJOU!qdzLk%;K@d#NKD^Jv~!Knv&$P%W+sXz6{7 zh{hSTjLrhhGCCLS=cD}s5j&Exh%OpSXvJ6ty=P&aL#xJl;J&mffV>OnvT+f8XRH9` z%Bo?jp!@JRi%%1<{Vhi08`iXI%oyh>gDo-8kK4tWTfja>#2@WvF9pLCbS;*v)~! z9P|35MRQ|gb3^g0i{v`H&UcQzTUjr2GKAsZiBK31ZL5q6~LVdwy;9G?Y0Oq(@wM48~%hqwu@?3YTQ zb{x-D^3m--NU7ge^02)m_;7;s(UdKrcawIgBX5VkPB2b8F%J49b7h!_39ikrIAN34 ze$Q&{LwhMd7k$gYwSJfxI>DEMrd0;MO@rJ>0>e(~Ky=7tITVSB)(`-DrJ1zE0D#gcdpvzcrZ$x`s&|%EJLLbI5csNCT9H*}^ zjL)(XPj0FC7h1Kzr9!E$^OU-~YerDAw%aJxs(P>-hUAcTh+_5o5W}b#c@p8aHL%%n z?W4Vu2+=n-VfbN?2IL6N#&|-jZkMVWm#S(-^UuH}2zI87j;f+>QF`e4$b@M_P^3<2 zQtYcNZ0iBTI&p|?g~k4INa6Xxvu~ADAue$SP8qu$);;0>>09}SO|Uz%@kGG$Zxv7- zIM^qxFD1-icWnT5)NJH~B)k(~gyeW)2n3f$;vu4rhpg}AL@MF(?~+V>UjpsTo;kw4&lRt(P4LBH?$Od;%f3;S)- zQ9QrH)AsrHnq5Z;V3ffk4n`hK=x%Nscm^(GSq4U$Fs@?z; zAfQrpp01P%g|hZat!sR)UaK|CX1$!RRf~MKp;dOvYD3fc!Yh5d6w;SVc{MC*K3h;5 zYN%G{7u05B$J|wQ{Z*}AFkhE?1n<`B$7G>)T`!NhB4f%rpFiO;0axcs6Ns^^{Mf2uy;d?*v{Er2fh*r%&8oVhiHvICzSpXPyGl*3U9GzP)h=B z!zKxHb93TCTuMrDDVCZ^Wu$aWniFGUDi-@J{Vjc#=3~j2m=L9Z0L}nTnpmHtB`FqN Si9{UElORI`N#f*{68{Byd79q< literal 0 HcmV?d00001 diff --git a/SGL/__pycache__/settings.cpython-313.pyc b/SGL/__pycache__/settings.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..affc4c1c0cc887e4a325be1f555624bb0bee71b7 GIT binary patch literal 3087 zcmb7GNpIUo7N+*ilx10t9cPoX%NbKn(snNhGEGagt&X;+{ zE}Gi_bLqWi1^23p&Y%RE15^TCa>jXQTv&Cby)=$4 z(^<4g6X3xd{4b#^bROid+VY@t0bQe)(RI2Ayc;%;UO`EE6)n+g=qA06ZqXa?Pomp& z3EiPLYfJPNx=U}j?xpT4_aRN;?7pJ4^rV4JlV~j?+0+5Ol}~o4zK`ps5Dsr)4O7L$ zjpXi8@?OKiuPBW+(UOL#P;-d9m+Ts#AvsjICOi_>L3$JPwRMVxU=*zZhA^SYLq+XkA10)@)T%VJk6E zBh+=xq-0lcl55RQa=Yf9b!CESi(t((k2=_}<|j4{Y#5O4k2l(|p|n6^aZWka4CzfEu(ZWMFtf z@ar+?mlM9&(T)2d4x=5!Iwm+7#3j7hD3A_$e#5B8P%0koI!mrbg)aj9dU zj4>t`gr*g`R5h&hP=krv9Toak*acCnHAa0UWSthS4z~^F0Z|qj!3`F7it3GNAAB7g z)Txp3Sj&@YKSl`@{{UTPS`UWU^MbZ>_6fY5OY89j_&iUa5E$*HyezOGW}ZpKEc0e_ z6~uyKxhy+Wpj58rN=0NP?3BDVT0~Gf9mt_mj4aT=O{J@v=e6J1y~vR9gGx;N*a`!4 zNT=M)FBP|PMTvQfVnL#DxCyN738$T^=qQHqTBi*eZX42Y%n3UNrlM)Lb=Sm*w27+N z#r|S|(5dzGb2Sx+M%vwW9&0Ug??V31pDRCTg7VPE3kBbPu7YB>jVY;rtigx1l`hoL zPBmi%;GFve~@! zQmja9s!}Rd<(*1CQz~wYPKEr>hSZMiHW z^s-dR$}hxx4mL~B3w&NIZtaL$lAI}JB~X|vNb;)^RB&(y9L_!bs>u8{Rec4XS3z^e zw$5S$dNY@o(4d#%S!q+;$ya5tRgyPzQa;N<1u2^o9f9zGwB2XCR1kA{dDNBR!O{+% z4e4^Jat^btBa|OWInLw}o4$~efmdO(V~kO#?A)u(N~s__h>;>Y)Y4A%7w!X`9mm!) z-_-05G-})BS{54z@C8vbsa{j{7JMuaxUOn&OE~}0SB20yV!=N}qxn`*YH$ z!`Sz@T&{QSu*>_u1ZFx86pUPa?~2BM(m^4|~CW zl#5ney>Q>ph4`NDEEeza@57O}yBB@G7>v4MC&9%QdsF=&mylflo|*e`?`Pl7fBSXj z@p0^n)5OBrRPsINy%p_y{E6_pP{il&dwAa63-zyaiREK11{QqL)3|UNTlne8N$lP` zpC<+wpMzQCLes~wSACBg4DnQN`t;JxV{Z0z?ly>?#^QhH=@Ury?~A_hxc~qF literal 0 HcmV?d00001 diff --git a/SGL/__pycache__/urls.cpython-310.pyc b/SGL/__pycache__/urls.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..0e094083788a9c84226d8404d4cfc892eaee7b72 GIT binary patch literal 1958 zcmb7FUymC#5Z~R~{M+Qx+`r~%X)!#Ii*(6CB_tF9qJkDqDimGIOJ4T&VkdF5yWZN~ zqm6j$b3X{*2wCEZr+x$~ff#$e*XVSWU?W>Iw)q$4Dkjg>`Wc(VlQ!1Z|b>P-b%Jof9j{TY0c<^owm@r>8t%MwUwR;KgWR?94Ul_Q-T`^n%6qVT8}HlQ2cUKFO{?`m zyMYg__8#$8z15EKd<#}~@ol^EK4^RRj@9mhwvRv1+M+{Rq_H}HaTB9gUf-Ga@rO^G z;YabWp5p{RpFTn}md)v+;IX7ELvzN_lkXm(oU;{~$#D=oT@rLw@Fb6=Bs>#mD4{|k z&I(Bc0uKU7hAt@iMU2ry*q$;@5Y50-TKdcr5(|O^A(H^Xx0Es$lQ6_=CdPObXA4#x zH)Cl?vhcI28&P1reAsjElAb9XRPQjU&1P_aBX5uyH8n2&@(S3|joFSU#jLQi^ zbIwwfzKG&Hx5hF~gTH6-It87UM%HouKIneT87<`k&LX6HK zGrZyTT~RQ(BwPnFHW63hd=I|}_ud!DdG2n1Fq4Ya}d9Sny-@ER_lGjvrg z#wpE)p7J&2s$t=<(iB8W$VPx%7ZQ4D_S&_Z42jB7HJV}a900zq&APWBLbt^T`Uw|Q zhUTBQk=HPh&`8L^6;IE<&|a*&>of#e3Z}& z9#gTwh`O_}9$l_i{H*Jy9^rZy$6|TTVvaA#RC^|hpGs~|i(D3*toO;Yg61TJq(||H zlMHj9XYU&8`gW1y7;?U5EnMGv_afAH8y<^7pAm7!-mW582oSt)d z*c{c~=wrSG7VdAF^{wDFZRx+=JvW6Jm#xO@dQ(eJ@JHfs{lB8hGE`haZOYnl)iumS zwitqUHQE!D+>hW&tDqE5A3uJo z+8giIZw^N~Rz1D>IMfeSDBv|tLb!U+5%gI>LU`TH&|!`97pnP13U?(TU+KFg&S3JL p&R);$cpVtsEtt*Eb3NDB<8QBay;OI-e?0&CHM{eV?ospie*ry|ZjJx| literal 0 HcmV?d00001 diff --git a/SGL/__pycache__/urls.cpython-313.pyc b/SGL/__pycache__/urls.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..7b88f10e181ad4cba27f5e89bddde70c2588b65c GIT binary patch literal 2488 zcmb7G&u`OK9CuPDaU4Qh3Ts!|^tG&{fhOK6AwdRgtS!)%4VHj5iActcUlOy}4)59g zh<4cxPMju<<8Ir3)2Ii6rD=zW12?K_hu!vl&vr0vkT$DzUp}AD`~H3}-Opxa0iI9) zDI4b{LHLV(2%qs_u|FLbgr9|~K!j?n8sCa-#z`Ep^~l!9rbxui1WEAE;#P7qMN)j7 z*pfEWBn|6iHMJ#gW=IAJHE}_xO0`U7Ds=MhZ#7+&FN|Nl@g5D5eIAk8AM?I;^NH z9LCs9umaHK!)O&yI@PjM1`u)wSw8UhbD${j7wp=sMCY zWSAYBIAw$y#5R%nMAbT-0QBSJ`jtS>QeYWGQiQFLZEGo?Uk(y$*(P2_mS*BhdA80M zl7e(<4?t6ou`yFkyj|c*J2i*TL5RiH7M*8daH*rNV)THmrKv)eWl&Md1Ee zYOK9seKvSu5QGB#VOqRYK#ic3Wxrg0KT53PVUU4#nHS|hN4wp&n+g;#^ps}+x0^2% zWcdx7&_c{hXu4@wg}5iOl6$E@4va*x<3KhP)=BEXEY;tz+l6i7Mf3zOVOTnT42Z~j z(;aJK%EqDy^Q60mqjZl4h#DX~fB{-;*eQwIacmPM|y!L(uL?x1(#2^AJwyPJft${$}B_aG4L4*tYXcVaiLX zDqyPW9SuenCfy;%HW`5#@iLJ)CL$mt5rx^QAW4QyzT4g4jVbw~MpA4O`=%vn_R4TE zFF;r;=#Aey;vMygpc#~mGPOtz2YVtrO5Tb0cM`vN-dHe}s;2st^Ck}>s$Ul`{q_3V z#uXKgv?u$^%FUa%y-eiZ`d!!uzk;{2TCUxpn9$nwTeUSze}KER<`BCEClCh1c;Mn1 zT=M*vMOW%P@uZ6;9GN!0OxX7pJ7;tq-fu@@vDjXGJSP5qT8Pd6DJ;Gg&>zB?*TTeJ zQb?qq9(#J{`Q2xCe|gjs^RGl{Cw=n8cRP!p@6KM_6)$mM?$^nk!s_n)+OD|HfteT0 zozs_gbC-9;FNOhqX`wG=UrLKTX|bP0dnqxI+>^msUz+E{Oi!BWXXm2C5+}~~q_h3( za+DYY;<@}xem?qabU!fymLzUzhHp64lTP)s3(*ZZPUL!0?f|jK2|uU;-|_ZZY-u#U ncPl0&GEdLH%*^&Ov%h`+viM~We#9$#-va$r?57N2|1SIscGSkC literal 0 HcmV?d00001 diff --git a/SGL/__pycache__/views.cpython-310.pyc b/SGL/__pycache__/views.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..889c33c4f2546e55c0fd37babd85fc1eff34b3e0 GIT binary patch literal 8530 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
$hWbjS^S`D9=o|q| z@Y_*b7P_*(dQx6kYeGmtgor2#WH}~PHk)~=vqy)^&6Cp+IIio3&c}7h;SNdQl6`<4s0QHW9@VgVmHunPMk%K;Enml z>x(I;9>nYf4G79i!UR4()%R30@+^0e-sfi|U9C!BR~zIBMn|1VP=5FZsh#9j)a-f^4f#Np9XC(25+h~(reC@bh` z3CV7iKhRoEYphjiRhf1bL4(`noU+QwLJteE6V> z3sYbRE-2z!j6;>h%5jprsOdmK-4Lf~2q)hL%q;QJzDX10&;1!GI*1H}c*6Re2r>QJ zx`SAbabJ<*XNOUe4=5hSjZ?&01OD(RF&58bHaXq)8tJh4a8bIl4r+yRW%unc?H_2# zboI4KSlS8uv++sM#p?s0B#%b83p(mlEk%qJKen}ZQ2!qFa9E|_%+oC0iuqO0V! zW%2^92UC~cD1=0MbG7_CrXvIV+_>?XDKM7^! zq;>#)kI0{k#X;pGXgqYxq2ISpM2u6HAMv5|THqKw9*g-<{tLStfNCR9)!cy#i|;`` zMU%1%$QH%-ktd|_779@rT&xT7+RXX&yjVa(S%Ps3MMAFane0P{vKldBR_nCEWIw8Y zu)Reznf!u|i{L9F<`Gra$HbecP8UK!fC2m-p;zLniZ9FYvmuWzhVknZ{K|aYbnR_w zGs2pmEY^*9T_N~+0QnwzL{B5D>_vbW!D6T#3P>S1W&OjxU$YG|y7!IyhNbv)gr*Om zoEU*Jy`)t8rZ^VhiV{Vv6t5L0hek;XsJm~p$38D~>`8$)k6N8UMhqo)WfVsmj86&ra3iM* zGn`M6F7-OKR#vz+yn-XNbaHp?Ns1@eEaQH~G$!r8jPDj3D6Sunr%|=5`vX<9b z4dmQJ6)y*ON$b||JtI{t#Yck7AkMd;sDdcfL@KCWMsIm2>zIC^VjQH{ zgC2|K>HDo9lP|xPH6hs-{_;G1Wt#7|6!Zm2T%wkv9~|b@sOsxn>TbM5O)1=_e0jzF z71t1?iqwV&G@jCZ>d>5%SUkRSoWg0PpU5n2(izuh@JS3&0s}X0I?uwTIEplDP??LT M!$@COZ}pn~Pn=D4XaE2J literal 0 HcmV?d00001 diff --git a/SGL/__pycache__/views.cpython-313.pyc b/SGL/__pycache__/views.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..308fd04376b3854f1b4012ac450d41060ed0c767 GIT binary patch literal 11371 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 literal 0 HcmV?d00001 diff --git a/SGL/__pycache__/wsgi.cpython-310.pyc b/SGL/__pycache__/wsgi.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..9b653ca413239bbeb33be55631448b6aa1054f41 GIT binary patch literal 530 zcmYjO!EO^V5cN7~Q&eE!>si)LN_*u4 z_ysufJ=}cd#4m7SHW5-rnz6>?dGC1!kB(AC_UYYo^DSZQcbDv1pORPP{s{%mrc5WA z+hm&1*|WUvO?wH0WZD0|r~7*E2dAv}l}-0G&)IPQ_E-8LAB{zcZf+_u$5!N{3(>T= zgfe7lIt~K9H0Z&LumG`rtgKZZEePd>5;f|Tg~t}wV8vRsW>a#i1}$bY)ilB(5|3XTQrO)(IxeEVlDzTQ}ye;^#!h6N0B5Lmt~NX` z5wUWU)ueDYT+f2GjWyy*WRg0sptGDN9;Cm@h}A)mS^D|8O3UA z=S8=@ANtz|2c2%)58v#!4)?atm(1j@0<9@eRij!|!_d%&VPOeX+@FbXW24lf_^Rr^{`Rr{sW!*rSzk-x!w!b#U_@7n9mB|Byo!{u`4`h9GE}ZXZucBbM;A4@WP1Js=E<~) literal 0 HcmV?d00001 diff --git a/SGL/asgi.py b/SGL/asgi.py new file mode 100644 index 0000000..e4edf1e --- /dev/null +++ b/SGL/asgi.py @@ -0,0 +1,16 @@ +""" +ASGI config for SGL project. + +It exposes the ASGI callable as a module-level variable named ``application``. + +For more information on this file, see +https://docs.djangoproject.com/en/5.2/howto/deployment/asgi/ +""" + +import os + +from django.core.asgi import get_asgi_application + +os.environ.setdefault("DJANGO_SETTINGS_MODULE", "SGL.settings") + +application = get_asgi_application() diff --git a/SGL/settings.py b/SGL/settings.py new file mode 100644 index 0000000..a2e3768 --- /dev/null +++ b/SGL/settings.py @@ -0,0 +1,147 @@ +""" +Django settings for SGL project. + +Generated by 'django-admin startproject' using Django 5.2.6. + +For more information on this file, see +https://docs.djangoproject.com/en/5.2/topics/settings/ + +For the full list of settings and their values, see +https://docs.djangoproject.com/en/5.2/ref/settings/ +""" + +from pathlib import Path +from os.path import join + +# Build paths inside the project like this: BASE_DIR / 'subdir'. +BASE_DIR = Path(__file__).resolve().parent.parent + + +# Quick-start development settings - unsuitable for production +# See https://docs.djangoproject.com/en/5.2/howto/deployment/checklist/ + +# SECURITY WARNING: keep the secret key used in production secret! +SECRET_KEY = "django-insecure-3mmf81^pt+k6-^dj$n2&*kvf6m09n5i%*+ajv70(ynaxifj5fg" + +# SECURITY WARNING: don't run with debug turned on in production! +DEBUG = True + +ALLOWED_HOSTS = [] + + +# Application definition + +INSTALLED_APPS = [ + "django.contrib.admin", + "django.contrib.auth", + "django.contrib.contenttypes", + "django.contrib.sessions", + "django.contrib.messages", + "django.contrib.staticfiles", + "gestion_produit", + "gestion_fournisseur", + "gestion_vehicule", + "authentification", +] + +MIDDLEWARE = [ + "django.middleware.security.SecurityMiddleware", + "django.contrib.sessions.middleware.SessionMiddleware", + "django.middleware.common.CommonMiddleware", + "django.middleware.csrf.CsrfViewMiddleware", + "django.contrib.auth.middleware.AuthenticationMiddleware", + "django.contrib.messages.middleware.MessageMiddleware", + "django.middleware.clickjacking.XFrameOptionsMiddleware", +] + +ROOT_URLCONF = "SGL.urls" + +TEMPLATES = [ + { + "BACKEND": "django.template.backends.django.DjangoTemplates", + "DIRS": [join(BASE_DIR, "SGL", "templates")], + "APP_DIRS": True, + "OPTIONS": { + "context_processors": [ + "django.template.context_processors.request", + "django.contrib.auth.context_processors.auth", + "django.contrib.messages.context_processors.messages", + ], + }, + }, +] + +WSGI_APPLICATION = "SGL.wsgi.application" + + +# Database +# https://docs.djangoproject.com/en/5.2/ref/settings/#databases + +DATABASES = { + "default": { + "ENGINE": "django.db.backends.sqlite3", + "NAME": BASE_DIR / "db.sqlite3", + } +} + + +# Password validation +# https://docs.djangoproject.com/en/5.2/ref/settings/#auth-password-validators + +AUTH_PASSWORD_VALIDATORS = [ + { + "NAME": "django.contrib.auth.password_validation.UserAttributeSimilarityValidator", + }, + { + "NAME": "django.contrib.auth.password_validation.MinimumLengthValidator", + }, + { + "NAME": "django.contrib.auth.password_validation.CommonPasswordValidator", + }, + { + "NAME": "django.contrib.auth.password_validation.NumericPasswordValidator", + }, +] + + +# Internationalization +# https://docs.djangoproject.com/en/5.2/topics/i18n/ + +LANGUAGE_CODE = "en-us" + +TIME_ZONE = "UTC" + +USE_I18N = True + +USE_TZ = True + + +# Static files (CSS, JavaScript, Images) +# https://docs.djangoproject.com/en/5.2/howto/static-files/ + +STATIC_URL = "static/" + +STATICFILES_DIRS = [ + BASE_DIR / "static", +] + +# Default primary key field type +# https://docs.djangoproject.com/en/5.2/ref/settings/#default-auto-field + +DEFAULT_AUTO_FIELD = "django.db.models.BigAutoField" + +MEDIA_URL = "/media/" +MEDIA_ROOT = BASE_DIR / "media" + +# Gestion de l'envoi des mails +EMAIL_BACKEND = "django.core.mail.backends.smtp.EmailBackend" +EMAIL_HOST = "ssl0.ovh.net" +EMAIL_PORT = 465 +EMAIL_USE_SSL = False +EMAIL_USE_TLS = False +EMAIL_HOST_USER = "support.it@cerfig.org" +EMAIL_HOST_PASSWORD = "Cerfig2025" +DEFAULT_FROM_EMAIL = EMAIL_HOST_USER +EMAIL_TIMEOUT = 10 + +# ALLOWED_HOSTS = ['support.cerfig.org', '41.223.50.187', 'localhost', '127.0.0.1'] diff --git a/SGL/templates/BASE.html b/SGL/templates/BASE.html new file mode 100644 index 0000000..c33f25c --- /dev/null +++ b/SGL/templates/BASE.html @@ -0,0 +1,114 @@ +{% load static %} + +{% load tags_personnaliser %} + + + + + + + + + + {% block page_titre %} Tableau de bord {% endblock %} + + +
+
+
+ + {% if user|has_group:"Administration" %} + + + Tableau de bord + + {% endif %} + + {% if user|has_group:"Employe" %} + + + Gestion des produits + + {% endif %} + + {% if user|has_group:"Administration" %} + + + Gestion des fournisseurs + + {% endif %} + + {% if user|has_group:"Employe" %} + + + Gestion des véhicules + + {% endif %} + + + Deconnexion + +
+
+ + + + {% block "contenu" %} {% endblock %} +
+
+
+ + + {% block "js" %} {% endblock %} + + \ No newline at end of file diff --git a/SGL/templates/emails/email_template.html b/SGL/templates/emails/email_template.html new file mode 100644 index 0000000..5f6a176 --- /dev/null +++ b/SGL/templates/emails/email_template.html @@ -0,0 +1,20 @@ + + + + + + Message test + + +
+
+ Logo cerfig +

Réception de nouveau produit

+

+ Bonjour M. Sylla Soriba, la livraison de nouveaux ordinateurs au CERFIG a été effectuée + avec succès. Merci à vous +

+
+
+ + \ No newline at end of file diff --git a/SGL/templates/emails/téléchargement.png b/SGL/templates/emails/téléchargement.png new file mode 100644 index 0000000000000000000000000000000000000000..d907304601942f84e1be08733df09de25d5bb032 GIT binary patch literal 4808 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 +
+ +
+

Rupture

+

{{ nombre_rupture }} produits

+
+
+ +
+ +
+

Pré-rupture

+

{{ nombre_pre_rupture }} produits

+
+
+ +
+ +
+

Correct

+

{{ nombre_normal }} produits

+
+
+ + +
+
+
Demandes de produit ({{ nb_demande }})
+
+
+
+
Commandes en attentes ({{ nb_commande }})
+
+
+
+ + + + + + + + + + + + + + + + +{% endblock %} + +{% block "js" %} + +{% endblock %} \ No newline at end of file diff --git a/SGL/urls.py b/SGL/urls.py new file mode 100644 index 0000000..a20c2fa --- /dev/null +++ b/SGL/urls.py @@ -0,0 +1,68 @@ +""" +URL configuration for SGL project. + +The `urlpatterns` list routes URLs to views. For more information please see: + https://docs.djangoproject.com/en/5.2/topics/http/urls/ + +Examples: +Function views + 1. Add an import: from my_app import views + 2. Add a URL to urlpatterns: path('', views.home, name='home') +Class-based views + 1. Add an import: from other_app.views import Home + 2. Add a URL to urlpatterns: path('', Home.as_view(), name='home') +Including another URLconf + 1. Import the include() function: from django.urls import include, path + 2. Add a URL to urlpatterns: path('blog/', include('blog.urls')) + +""" #noqa : D212 + +from django.contrib import admin +from django.urls import path, include + +from django.conf import settings +from django.conf.urls.static import static + +from . import views + +urlpatterns = [ + path("", views.index, name="index"), + path("gestion-produit/", include("gestion_produit.urls")), + path("gestion-fournisseur/", include("gestion_fournisseur.urls")), + path("gestion-vehicule/", include("gestion_vehicule.urls")), + path("authentification/", include("authentification.urls")), + path( + "liste-commande-en-cours/", + views.liste_produit_commander, + name="commande_en_cours", + ), + path( + "liste-demande-en-cours/", + views.liste_demandes, + name="demande_en_cours" + ), + path( + "enregistrer-livraison-produit/", + views.enregistrer_livraison_produit, + name="enregistrer_livraison_produit", + ), + path( + "admin/", + admin.site.urls + ), + path( + "dashboard-produit/", + views.liste_produit_rupture, + name="listeProduitRupture" + ), + path( + "equipement-a-rendre/", + views.produit_a_rendre, + name="equipement-a-rendre" + ), + path( + "update-equipement-a-rendre/", + views.produit_a_rendre_update, + name="update-equipement-a-rendre", + ), +] + static(settings.MEDIA_URL, document_root=settings.MEDIA_ROOT) diff --git a/SGL/views.py b/SGL/views.py new file mode 100644 index 0000000..bfe918c --- /dev/null +++ b/SGL/views.py @@ -0,0 +1,334 @@ +"""Fichier views.py de gestion de la page dashboard de l'application SGL. + +Principales fonctionnalités couvertes : + 1- Gestion des stocks des produits (rupture, pré-rupture, normal). + 2- Affichage des commandes en cours et validations des dites commandes + 3- Affichage des demandes en cours et validations des dites demandes. +""" + +from django.shortcuts import render, redirect +from django.http import JsonResponse +from gestion_produit.models import Commander, Demander, Produit +from django.views.decorators.csrf import csrf_exempt +from django.contrib.auth.decorators import login_required + +import json + +from gestion_produit.views import calcul_stock_produit + + +def dashboard_quantite_produit(): + """Calculez les quantités des produits en rupture, pré-rupture et normal. + + Returns + ------- + dict + Dictionnaire contenant les nombres et les listes des produits par + catégorie. + + """ + tous_les_produits = Produit.objects.all() + + nombre_rupture = 0 + nombre_pre_rupture = 0 + nombre_normal = 0 + + produit_rupture = [] + produit_pre_rupture = [] + produit_normal = [] + + for produit in tous_les_produits: + stock_actuel = calcul_stock_produit(produit) + stock_actuel.pop("image") + if stock_actuel["stockActuel"] == 0: + nombre_rupture += 1 + produit_rupture.append(stock_actuel) + elif stock_actuel["stockActuel"] < produit.seuil_pre_rupture: + nombre_pre_rupture += 1 + produit_pre_rupture.append(stock_actuel) + else: + nombre_normal += 1 + produit_normal.append(stock_actuel) + + return { + "nombre_rupture": nombre_rupture, + "nombre_pre_rupture": nombre_pre_rupture, + "nombre_normal": nombre_normal, + "produit_rupture": produit_rupture, + "produit_pre_rupture": produit_pre_rupture, + "produit_normale": produit_normal, + } + + +@login_required(login_url="authentification:login") +def index(request): + """Vue pour la page d'accueil du dashboard. + + Parameters + ---------- + request : HttpRequest + La requête HTTP entrante. + + Returns + ------- + HttpResponse + La réponse HTTP contenant la page d'accueil du dashboard. + + """ + if request.user.groups.filter(name="Chauffeur").exists(): + return redirect("gestion_vehicule:index") + + if not request.user.groups.filter(name="Administration").exists(): + return redirect("gestion_produit:index") + + commandes_en_cours = Commander.objects.filter(livrer=False) + demandes_en_cours = Demander.objects.filter( + valider_par_chef=True, valider_par_logisticien=None + ) + + gestion_quantite_produit = dashboard_quantite_produit() + + nombre_rupture = gestion_quantite_produit["nombre_rupture"] + nombre_pre_rupture = gestion_quantite_produit["nombre_pre_rupture"] + nombre_normal = gestion_quantite_produit["nombre_normal"] + + return render( + request, + "index.html", + { + "nb_commande": len(commandes_en_cours), + "nb_demande": len(demandes_en_cours), + "nombre_rupture": nombre_rupture, + "nombre_pre_rupture": nombre_pre_rupture, + "nombre_normal": nombre_normal, + }, + ) + + +@login_required(login_url="login") +def produit_a_rendre(request): #noqa: ARG001 + """Vue pour obtenir la liste des équipements à rendre. + + Cette vue est appelée via une requête AJAX et renvoie une liste + d'équipements qui doivent être rendus. + + Parameters + ---------- + request : HttpRequest + La requête HTTP entrante. + + Returns + ------- + JsonResponse + Une réponse JSON contenant la liste des équipements à rendre. + + """ + equipement_a_rendre = Demander.objects.filter(a_rendre=True, rendu=False) + liste_equipement = [ + { + "id_demande": equipement.id, + "produit": equipement.produit.libelle, + "quantite": equipement.quantite, + "detenteur": ( + f"{equipement.user.user.first_name} " + f"{equipement.user.user.last_name}" + ), + "action": equipement.rendu, + } + for equipement in equipement_a_rendre + ] + + return JsonResponse(liste_equipement, safe=False) + +@login_required(login_url="login") +@csrf_exempt +def produit_a_rendre_update(request): + """Vue pour mettre à jour le statut des équipements à rendre. + + Lorsqu'une requête POST est reçue, cette vue met à jour le statut + des équipements à rendre en fonction des données fournies dans la + requête. + + Parameters + ---------- + request : HttpRequest + request.id_demande : int + L'identifiant de la demande d'équipement à mettre à jour. + request.action : bool + Le nouveau statut de rendu de l'équipement. + + Returns + ------- + JsonResponse + Une réponse JSON indiquant le succès de l'opération. + + """ + if request.method == "POST": + data = json.loads(request.body) + for d in data: + demande = Demander.objects.get(id=d["id_demande"]) + demande.rendu = d["action"] + demande.save() + + return JsonResponse( + {"status": "success", "message": "Produits mis à jour"} + ) + +@login_required(login_url="login") +def liste_produit_rupture(request): + """Vue pour obtenir la liste des produits en fonction de leur type. + + Cette vue est appelée via une requête AJAX à chaque fois que l'on clique + sur un cadran (rupture, pré-rupture, en stock normal) et renvoie une liste + de produits en fonction du type spécifié dans les paramètres de la + requête. + + Parameters + ---------- + request : HttpRequest + request.type : str + Le statut de produits à récupérer qui sont en "rupture", + "pre_rupture" ou "normal". + + Returns + ------- + JsonResponse + Une réponse JSON contenant la liste des produits correspondant + au type spécifié. + + """ + type_encadrer = request.GET["type"] + dashboard_gestion = dashboard_quantite_produit() + + donnees_charger = [] + + if type_encadrer == "rupture": + donnees_charger = dashboard_gestion["produit_rupture"] + elif type_encadrer == "pre_rupture": + donnees_charger = dashboard_gestion["produit_pre_rupture"] + elif type_encadrer == "normal": + donnees_charger = dashboard_gestion["produit_normale"] + + return JsonResponse(donnees_charger, safe=False) + +@login_required(login_url="login") +def liste_produit_commander(request): + """Listez des produits commandés non encore livrés. + + Parameters + ---------- + request : HttpRequest + La requête HTTP entrante. + + Returns + ------- + JsonResponse + Une réponse JSON contenant la liste des produits commandés + non encore livrés. + + """ + commandes_en_cours = Commander.objects.filter(livrer=False) + ma_liste_commandes = [ + { + "id_commande": commande.id, + "produit": commande.produit.libelle, + "quantite": commande.quantite_commander, + "date_commande": commande.date_commande, + "date_livraison": commande.date_livraison, + "fournisseur": commande.fournisseur.nom_entreprise, + "is_logisticien": ( + request.user.profile.departement. + nom_departement == "Logistique" + ), + } + for commande in commandes_en_cours + ] + + return JsonResponse(ma_liste_commandes, safe=False) + + +@login_required(login_url="login") +@csrf_exempt +def enregistrer_livraison_produit(request): + """Enregistrez la livraison d'un produit commandé. + + Lorsqu'une requête POST est reçue, cette vue met à jour le statut + de livraison du produit commandé en fonction de l'identifiant de la + commande fourni dans la requête. + + Parameters + ---------- + request : HttpRequest + request.id_commande : int + L'identifiant de la commande dont la livraison doit + être enregistrée. + + Returns + ------- + JsonResponse + Une réponse JSON indiquant le succès ou l'échec de l'opération. + + """ + if request.method == "POST": + id_commande = request.POST.get("id_commande") + try: + commande = Commander.objects.get(id=id_commande) + commande.livrer = True + commande.save() + return JsonResponse( + { + "status": "success", + "message": "Livraison enregistrée avec succès." + } + ) + except Commander.DoesNotExist: + return JsonResponse( + {"status": "error", "message": "Commande non trouvée."} + ) + return JsonResponse( + {"status": "error", "message": "Méthode non autorisée."} + ) + + +@login_required(login_url="login") +def liste_demandes(request): + """Listez des demandes en cours de validation. + + Parameters + ---------- + request : HttpRequest + La requête HTTP entrante. + + Returns + ------- + JsonResponse + Une réponse JSON contenant la liste des demandes en cours + de validation. + + """ + demandes_en_cours = Demander.objects.filter( + valider_par_chef=True, valider_par_logisticien=None + ) + is_logisticien = ( + request.user.profile.departement.nom_departement == "Logistique" + ) + ma_liste_demandes = [ + { + "id_demande": demande.id, + "demandeur": ( + f"{demande.user.user.first_name} " + f"{demande.user.user.last_name}" + ), + "produit": demande.produit.libelle, + "quantite": demande.quantite, + "motifs": demande.motifs, + "date_de_mise_a_dispo_souhaite": demande.date_de_mise_a_dispo_souhaite.strftime("%Y-%m-%d"), + "a_rendre": demande.a_rendre, + "valider_par_chef": demande.valider_par_chef, + "valider_par_logisticien": demande.valider_par_logisticien, + "is_logisticien": is_logisticien, + } + for demande in demandes_en_cours + ] + + return JsonResponse(ma_liste_demandes, safe=False) diff --git a/SGL/wsgi.py b/SGL/wsgi.py new file mode 100644 index 0000000..82babd0 --- /dev/null +++ b/SGL/wsgi.py @@ -0,0 +1,16 @@ +""" +WSGI config for SGL project. + +It exposes the WSGI callable as a module-level variable named ``application``. + +For more information on this file, see +https://docs.djangoproject.com/en/5.2/howto/deployment/wsgi/ +""" + +import os + +from django.core.wsgi import get_wsgi_application + +os.environ.setdefault("DJANGO_SETTINGS_MODULE", "SGL.settings") + +application = get_wsgi_application() diff --git a/authentification/__init__.py b/authentification/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/authentification/__pycache__/__init__.cpython-310.pyc b/authentification/__pycache__/__init__.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..59bbc1930479ff43627eab1bd9cf3bc1a558b450 GIT binary patch literal 148 zcmd1j<>g`kg7^1?GC}lX5P=LBfgA@QE@lA|DGb33nv8xc8Hzx{2;!Hyenx(7s(x{P zQEHBUPJVi3aY<%jX{vs(yN`ZiX-P(EUP)$JW^!UlW`3T2e0*kJW=VX!UP0w84x8Nk Rl+v73JCK3JOhAH#0RSVsB0m5C literal 0 HcmV?d00001 diff --git a/authentification/__pycache__/__init__.cpython-313.pyc b/authentification/__pycache__/__init__.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..cf7afde514ecbc52fa525a010d3c45d6c6a1da78 GIT binary patch literal 164 zcmey&%ge<81n=(&WrFC(AOZ#$p^VQgK*m&tbOudEzm*I{OhDdekkl<_XRDad;?$zz z7>|G$m(=3ylKg_0lA`>Woc#36;*!k5($tt>cb}NV(vpnSypqhc%;dz9%>2BV`1s7c n%#!$cy@JYH95%W6DWy57c15f}GeLG1gBTx~85tRin1L(+og`kf*YNdnf^ffF^Gc(44TX@fuanW zjJH@5Q*tx&{4|+v@ug%X=B4NBCFkdr6lEqAfecv5P{abHz{D>T{fzwFRQ=-oqSPGy zoc#36;*!k5(p3FmcOU)4(vpnSypqhc%;dz9%=|oku(5gtmA5!-a`RJ4b5iXXfd&9Di055ng;s5{u literal 0 HcmV?d00001 diff --git a/authentification/__pycache__/admin.cpython-313.pyc b/authentification/__pycache__/admin.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..0b67d816940d6b39195364b29dc569f507658667 GIT binary patch literal 208 zcmey&%ge<81UEV@GyQ?|V-N=hn4pZ$0zk%8hG2$ZMsEf$#v(=qhIA%P=9eI8O~zZS zi7C06d48HqxA;=B67$mY^^)`RN{TX*ikN{4Rx*4Bsk`OiY!wq)oLW>I;}Hni>=A?h}((T9T2PSCW~QnVeXXnV%N}HeIiv@)n0pZhlH> cPO4oI2hc!9AT9l~RcuJCS(1T;0ihNox}Xkp%VL?HlNy{jjgtXZ_%ra6yfX0@ zm^inUsCv>p`|jSov(Jo1eS-G#c%{DZ{Pw}Vg&0iG?F9l5pqi94qm;}D1i(HBFiGE8 z7C^WlaqkCNB&P0oTGw}`%2l!SnSG-eOwjEZL6VFD!ETx{2(l0us)X)r+O;cLwJKLj z(JE7IwcgI*SyY8d;3+8$NNtl_RUp^gE2+Vqh=aCy+;b79+x#)DuQNZwgBNqDFCu#hCHt>6yu1qOYYZ|FjZ3<;uweDoPm_4M2lT%UGHmP45 whV6cd_6Q*&A&uxJH;5bd6sUDuDruPBK`Q4hjg_7)HkgC7{tAd<#|(9n!Ky<^95daUj_m}?;a zK*(RvU*l04Jmus~*m$?vSuggX>OEe)qN=OkZjTUr=Ra1}E#`loyuHQ%^j8pE6Gj+4 zAo~>PBKb&`2@B>33pxD~)^!kMQQUa+B&Ke7vn;oD(NkHsmg`6dr2iSgHQ@v(BM>kO zAqya4Av9P7&8!hO-Rx#%&tzd$PjwTkbW!(vjL`aPKK+>#neL>goeQ1H+;p~7h6cT> zWS+W-2NFm&a5a_FNkH>_#tde}7j0@3IU~H}mS!k4}QrSzY+zRZe zQS<#HU+iXtFcwGaio{w_ru8%-wf!&-;-y8>DBcDItP@{ literal 0 HcmV?d00001 diff --git a/authentification/__pycache__/models.cpython-310.pyc b/authentification/__pycache__/models.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..b44afedf8f4bde2454a048a1bd44e6b26b76e4f5 GIT binary patch literal 1736 zcmbVM&2Ah;5T3uC*&Xl3RuT|`OA8^)9x|H?mk1FX+X)C`5Oywe8I7lF?OA%dH{CN4 zwz!e2p8#>sUU-RpixD?Yh&S*hRP}Di#DNRF>QYsAO>I^6_mvurVh7h>*AL2jJ;(Wj zjP451*uib~QE(@9xXV4^R$l74r2E3Jf;4cQ#|{s8@43T!;LUnJ`)PARTAxI` zf9#A0&6gPJ8^xC|1Q<3~jb>syZ|ZZ9bvZ4Iye^ewP&1LUGceZTg&*uiZ+LIFSPs>=B5iZGeLfS4{EO%S;LbaJjLm>8u&OoTcsvGY$Gm>fSooZNh! z$*SAQ{GyGr%+xx|MwGUPBJ?irbQ+he?~lg)wx8Luv#gD?3_~;mP#2|~hnS|3mZbPE)1n$rqdiL}!C{S;A$dzz-6ABO_ zAR_Kvd1)WD0mLXbxR1Z!DoBTDjd+iT2$x$N0sY)bH~9dcDQ=_hEI^_89pnBxR0OP1 z+y!wG#|+n3f-M&{NY2m;n?v+qgk^fu{aG&06w9AMfu>=loGM*erWj_L`CKd)1k=34 zS5Iub1IaF!&S$EzD3z+tD{`UmUA$6wvE3mRQO|6bf&sG7kiU&roWpb#8NoDA60szp zhLf?c?_j}gAR8gt-l@pt56yi%*~2(*gf;a&j7o7VOmC#|P~-e@-l7D(mZijps1PM) z?k_latmdKSq2|v5)cjwGwn4Ltj{l!7t0|LQyX?|qpIp1+ajy*;e1m1GHQ865WaL z-|V`LU(+^sQ4qVfqQH%@hQRkw4g*cMNO7BPJKz?s2|rzB{{Gr7l&p1mn$S2&RwG2) oGI~fC5H@EUsnb16cA|LO{|rCDk?}cANkiv>gDiJ%2k*vz1KG~nQ2+n{ literal 0 HcmV?d00001 diff --git a/authentification/__pycache__/models.cpython-313.pyc b/authentification/__pycache__/models.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..ccab77e7a46a3331a093c79dbb06245b1ea0cc6e GIT binary patch literal 2303 zcmbVNO>7%Q6rNr0+Us=^yZLJfg^rrw;?k~CQ4R^HRY>|n6Vl3?ii@Sy#yfVmUGKUx zyA|QmoGN;1IaI)ja-z9Z<-`@qR}M)oPFF&zgg8`OQl-6c;?1lBb|?ZdmfpU3@6F7c zH}Ctr+uyGv7{C2K{4SY;O?Af?Zn3y>{k_I)`V>k+3&t-NFD$^3pnCdv9nwh5AdZwhsxp~sGX-FE7 z?lTR7qaujTeJ~|W+FEDev;7c9K6YB`e})^;2!t*L4eUfc4m`6i#eFvkT?rVme7ixa zQj&&{T<68!9S3nAT|s4G?iG_zhUg5~$|QuE`UFlV-T5SC^>Ov8-FgHrhv2GB?P}P1 zNTIx)lnf|g-VYj<^Vc;YIfW6g#&{w)o}HVi@FKIyh0B$B!mfuwvl7yv;stdV-s?t0 zD(3mc%KkU4ByVIiSL2Ljv5;C;Jk(W9qhsucQ`i8AHS{z;)Xq$+`K(`je${t~+re&H1-*AsvOpc&R4m@Lj z_m~R&)MT^@{Cs|`U%9V``;rS)OLf` z(Djcz+*%Kb?_h|4_v2K6c}wx8oWExK^#I#9Nfo9HyM8U84Z#Wwv#8nhTI(EqwhL`* z=x2Srim81qhy>*PAha9Y&A09bAK%(L+C?6mV%SmF!vxrd@p!#@mDCI!5ReUg0DwnA zvRq2hH{gP?;zynrt1F)EUyr81G6(B>wqxN5*p2TYu(j{_GnBVW53YGv2wdL-<)3g} zmchAi3;!C$cG9RYe0TNE zYKJriCLhc`aK3ZDb=$@1&EoXNTQfUIdcUw;7;YEvW&yVgQ=5gUjr_^S2X<0Y|EZl+ zDyt`u<*mI`8l*$;r5sk2lQ$jZ;vg4-M*1)LWH|tlPzkSooSB<7=Vs^6(g{A(&jpmY zb$@}Z3g(D4^X#&e0+a5U&#A6*WpF literal 0 HcmV?d00001 diff --git a/authentification/__pycache__/tests.cpython-313.pyc b/authentification/__pycache__/tests.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..c96f5d3abf1695af9ce86c2251e5af41fb6d4a9a GIT binary patch literal 208 zcmey&%ge<81n=(&W!eMj#~=<2FhLog1%QmH48aV+jNS}hj75wJ4Czdo%r8OGnvAzN zLQ;!MoD+*v{WO_wai?S@=B4NBl>o(xn1KpbGJFQ9yXD|)6%$&VT2vh45fI~&TAW>y zUl3DLlpm9mpPpG cPO4oI2hc!9AT9J5VgJD&2D~h0E%=dO%{m`Aw+>hgD6P1&B}^R;>c?+{_wj42jNO?sd9x# zAjSNZm|PxG{=$l%x`vJGlBeBiWe7;58Gq4GFppQm=tqm)>5ZV%{mcBT>NqO z^C}M7mYY@E0)Y$kMcxtnb^@Ytu*AD&38s3XFJRwfjW&C=n^`&+Cop xMD2_fs!qzz%cmgfGt5VgKBiY(>kiQMn& zub9F+Vf0j}>G$m_Xz?tgXWB`5Deth%bY{sBRbiX{=eDCjmEyR~TXC$3gCy(lS^=p5 zNBb)To=JX^=dtMpvoJ9GRH0VsK_rDt{6<54h192wHS$$Z5aja?*`(r7@|;NE#0(%L zJ1!`}TVKfgVTpOMmVZcv o?mNBVKlrb$uDjfG{i}ta-k(a;twguwu3H~?&Xj!_!i=`~2hp^T&;S4c literal 0 HcmV?d00001 diff --git a/authentification/__pycache__/views.cpython-310.pyc b/authentification/__pycache__/views.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..648d9dbc6670e45619b79c3b0e7e9e2a162f3ecb GIT binary patch literal 1127 zcmZuv%Wl*#6t$iA%(N6*KnNtV0F@w=*|4e*LPDY&C`ePW$YvB`(@7i0#dc^JrK@4f zKftoz(ZBGP6~6#N;yP`IX~9vhkFV|P<8v&QmU;-auND&2aAos;2HdC8v;cc zqL`8jbCMD6WDd4tr*gTMdEC!@9%Mn6bE}X?S=3>#>hXTo2kg_}Gs*@uq!IK>v^PRY zf118+n2PsBBjaj4Z}f!Kx_n<2xh_Q=Q^UL|(Q+W63kMkm;WoGF#>Fa_8vVfSHyZMC!JL2v)(@GA;|;v?LmT|~(q zkq-gEWpAM)(jga+qe)9zhk9Sgk=we|Z?L?lofft3j9{c)?alBAY5!}`A{uR#Q&jgZv0K2su*adUS#EM)E48e?A^g z1ZP7fB&#|uN|&%}INE$Uyi8~Kv1A7--T!2wxpKCwx&y%_J#4=L2?2$8fC(X(U?01` z zSv{MBT3VLxQp;z-Da*nvUtDu)S_D$3owBD+TCKXH7l?M0JGS8yE@)G+r&d9=48cV! MWDVp7;hn+tKatrWYXATM literal 0 HcmV?d00001 diff --git a/authentification/__pycache__/views.cpython-313.pyc b/authentification/__pycache__/views.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..6f502f19a8e18df08291c97628d8741289ee36b5 GIT binary patch literal 1446 zcmZ`&TW{P%6dvF0c(ZBP(n?vWHA$*q+87>)5J|*ET#7a{iE0)_+Lc!BddM1f?Qm?9 zvJzF1kcfDp2vzXFLtpbd`Uf^@AGV{QRw4-TRI&KusA-c_(}K;{zij^3ZYOX*U>*cTyb%O5U)lE#`E?Z`^l9QT!rE@qH-3MYJAGZ z#*C}HE{1YdzA;5eO&jgY3&ZRdsTuihEu)IB7KZ3&Nv)7auNQOgXr4x#u6iujWFEtP z&DE>IE5ZV=9LFrNjr0;aSMTov?OJWmYDQs5Z~iYC?=yLQ&Hae!X-pyXI+W>KUL0>n z;M*c_P%w_Bdu281SpM8GBCRO3I#GiBTKojHg0L9@=h5kwa~g9Myqq!Vw31Gnoj)CH z&}J)2sckT|Lz7nIgURpZ-33l5pr8rx_JNLuDHH&2;`Q1J(|~@C`b&WK?FccGc||c# zV)4P=dS|g-#w zoW=MnG`Go<3o|{r+}DcV-un91&*vU!7yG5DpO$}EzBjg4y1b*GTpdi5?``Z&yuBko zF(>xS@_u3R&fLR-wO=a#^4^bc_6pPc`kC*G-xcp{_pH^2`r3gx+1Drf`lY@x-J4zN z>B|F6E~rn5tf&J7Ku){@-k0nZIOyCZwb2Wyj`W6V9IA!jD>+i3Ev7Hxp(Ew^_jgA{ z|Mw+#&z)}8V#YHnhd+UgH(LNM)|jKPpoEs0J{={6^SE=7|L{DT+vGqV+j;GqwSBYH zJA37UIp34#fk#&DBGVcTKWa7_?2P}Z7j8yQ+=?J+rb(P>A-j&1hB3S$f#8P25gwBg z$Hj^#|2b5Zf#f?G*N0N$6ldsmNrvDMyT06s{IpHqfD0JsMa3_mc`6Bl@QA$n2bq6N ZmiEZfuVm(TQvOSQPEZFgNrIE5_!koZT7dun literal 0 HcmV?d00001 diff --git a/authentification/admin.py b/authentification/admin.py new file mode 100644 index 0000000..cced46a --- /dev/null +++ b/authentification/admin.py @@ -0,0 +1,3 @@ +from django.contrib import admin # noqa: F401 + +# Register your models here. diff --git a/authentification/apps.py b/authentification/apps.py new file mode 100644 index 0000000..d71f4e3 --- /dev/null +++ b/authentification/apps.py @@ -0,0 +1,6 @@ +from django.apps import AppConfig + + +class AuthentificationConfig(AppConfig): + default_auto_field = "django.db.models.BigAutoField" + name = "authentification" diff --git a/authentification/migrations/0001_initial.py b/authentification/migrations/0001_initial.py new file mode 100644 index 0000000..6e7f7d0 --- /dev/null +++ b/authentification/migrations/0001_initial.py @@ -0,0 +1,33 @@ +# Generated by Django 5.2.7 on 2025-11-11 07:12 + +import django.db.models.deletion +from django.conf import settings +from django.db import migrations, models + + +class Migration(migrations.Migration): + + initial = True + + dependencies = [ + migrations.swappable_dependency(settings.AUTH_USER_MODEL), + ] + + operations = [ + migrations.CreateModel( + name='Departement', + fields=[ + ('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')), + ('nom_departement', models.TextField(verbose_name='Nom du département :')), + ], + ), + migrations.CreateModel( + name='Profile', + fields=[ + ('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')), + ('chef_departement', models.BooleanField(verbose_name='Cet utilisateur est-il chef de ce département ?')), + ('departement', models.ForeignKey(blank=True, null=True, on_delete=django.db.models.deletion.SET_NULL, to='authentification.departement')), + ('user', models.OneToOneField(on_delete=django.db.models.deletion.CASCADE, to=settings.AUTH_USER_MODEL)), + ], + ), + ] diff --git a/authentification/migrations/__init__.py b/authentification/migrations/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/authentification/migrations/__pycache__/0001_initial.cpython-310.pyc b/authentification/migrations/__pycache__/0001_initial.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..969ae7863eaf9edeba118959aa15422653b1db3d GIT binary patch literal 1197 zcmZuw&2H345O%li8IQ-4gb*UJ;xGra+7awb_KFY?@&kw@tac_BUo6jbjnhusJ+y6h z!*%zXcYq`JeS>|Az9A$e-e84LpxTBcthTK#S9RClSJfqZJ>SCh{_QIN$+fI^M!38j z6dvF%?jT_nBf<&^{;8mu9ood4*}}=((9K$5i&&2=<}mj!i@D&Y?LY0X&B)jqv_7D{ zbub{>E1)cSo)iPB{fs9nF1gGL-O3~bQOu0q5~!nxl#$Q|=ambswEdbS zB=o>ZJB%_L{ItsmewYPoojP;M+ISW)k9AJToF`h%?q15~%gfRJ>&+0A@FWn+!cPiri7&EGb&>fj$ zcmXA7T1xFy2zo%3L8R6VtiihWq8fJ;X+Mhay;K5_52EOK6$^t4r8dubiPcgz8tJv- z_js|0r>KarA!m@!P82m)%bSOj$I;<<=eKD8+4jz!4$d_=6uP@rw_@MCN@d1C2M>9& ziA~xyrPG}W{82V+@K8ztao$M&u2jI2{3&*>#nL!Wq^4}Dy&4_9b?uFJCegv+-k$C~ z%V8psG^XvX&GFXe_Kx=D0=^E$8%y27=r#GcJ35jXj0%h(MnWdMDEadWM&n0&qyH9r zbTM3`jg5_8qOXM+E>0AVy5-?6eykaX`nL1gaVc4&ON5>|XHL7}Z;&4d{p6f^|JF7G zPhW2!4cT~AYpoTo0$$Z`vx^r$(_oOan?d<|s!`(La-rc6L_lU{Q MBuGcYDUP)O~sW;T2bV9IRS9;kcr$y>!&2p2I>`=$fj_s}; zFO!gX-U||sdu0E?cmjzR9^>%f>PUzoB&5A%D!lXAUbl_}goKsY{;t38c0QkUbtO5t ze*d+XjK?_cH=j7YfDW#cB0Rq05Qq2;j`HvnHiY#EjmSPPvJqX6(b&33MVTAoMmZEc z&!LzSD|WxKKl8X82?-jn@_F%vPh8LQOtP?T6QgS71(vLlD%EUa8Wt04W*O^N>5K>N z)a%KF;76qd5m5p0G=c;g1>E#m_3(X^Q{u%;JO45t@}_y30L#914ag^gqDrbb)KMlN z0mYDr;`7lt0ZE{DzN20OCFl7$VOl_`dEp~!MCuNaP!DK~bku;Dl}vH8 zT~-|Ez{_>uz1Pk|8I%ob&Z60z{`>$- zY@JTl3kjTUv(z%KYt+UyY}ia7mj;^zWX#l*AZOjDQWKjo_&I{B(0dyE{PvOuGF-Z+F zS5=l&RXC`Qj^RD6s`njD_cH^kM^!6?TDDFMY?#1^6NA`LKpF)`^lJ@*EtXmey0hi)2kI{>mR=;)1?bzVUrmh+z?P1be8z}qI= zLeu!t0$N&FUSUbIj!#!qzp7d`RJ5dOwoS>NV`EEI={pe83H&)$T)Lv{Kmjdf?WVGf zt$o|9D>gM1-K-MJCifkzplh4T-y5X7*@Mc=%*?F%s&Z5HBN_+C!OfpzYaEu?m)!I2 z-bdG3B9}PlNtc?^rEer}{Hi;C^(See6%qQxN1Lr=ARK8*Bgfg1=h^_b|Z7A6^rzBzl@2AWUKp(oAdwb=G`Zs zdSiv=SfR0c=#CvVG7kaxiRj6*O?mcN^!vF6+Vzm)BE>@`7nMAuyGZwt<07ZUai8dq+6V4t_o04No?QC!dMmCB98~g*CUZ<`r(ag*DdTe?pD0J2QK`E zA2c$DtwhX^T7syv*V{=RQ2eHfmIkLU+L`d=B#U%0IZ&+{iD$6x%JlYimH{}6|H@p012 N~=l=iz literal 0 HcmV?d00001 diff --git a/authentification/migrations/__pycache__/__init__.cpython-310.pyc b/authentification/migrations/__pycache__/__init__.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..3da86f067f5a7be7ae617e98da647da5fdbfbdc9 GIT binary patch literal 159 zcmd1j<>g`kg7^1?GC}lX5P=LBfgA@QE@lA|DGb33nv8xc8Hzx{2;!HMenx(7s(x{P zQEHBUPJVi3aY<%jX{vs(yN`ZiX-P(EUP)$JW^!UlW`3T2Zf1HBm{qJFAD@|*SrQ+w ZS5SG2!zMRBr8Fni4rF#Q6OdqG008PnCbj?o literal 0 HcmV?d00001 diff --git a/authentification/migrations/__pycache__/__init__.cpython-313.pyc b/authentification/migrations/__pycache__/__init__.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..4506a477055a024b53f24e455221f51efb66bc9a GIT binary patch literal 175 zcmey&%ge<81n=(&WrFC(AOZ#$p^VQgK*m&tbOudEzm*I{OhDdekkl|G$m(=3ylKg_0lA`>Woc#36;*!k5($tt>cb}NV(vpnSypqhc%;dz9%>2BV+|2YM vFsnEwK0Y%qvm`!Vub}c4hfQvNN@-52T@fqLc#!qQAjU^#Mn=XWW*`dy?D#Jh literal 0 HcmV?d00001 diff --git a/authentification/models.py b/authentification/models.py new file mode 100644 index 0000000..59c6531 --- /dev/null +++ b/authentification/models.py @@ -0,0 +1,39 @@ +"""Modèles pour l'authentification et la gestion des profils utilisateurs.""" + +from django.db import models +from django.contrib.auth.models import User + + +# Create your models here. +class Departement(models.Model): + """Modèle représentant un département.""" + + nom_departement = models.TextField(verbose_name="Nom du département :") + + def __str__(self): + """Retourne une représentation en chaîne de caractères du dép.""" + return self.nom_departement + + +class Profile(models.Model): + """Modèle représentant le profil utilisateur. + + Il étend le modèle User de Django avec des informations supplémentaires. + En y rajoutant notamment le département de l'utilisateur et s'il en est le + chef. + """ + + user = models.OneToOneField(User, on_delete=models.CASCADE) + departement = models.ForeignKey( + Departement, on_delete=models.SET_NULL, null=True, blank=True + ) + chef_departement = models.BooleanField( + verbose_name="Cet utilisateur est-il chef de ce département ?" + ) + + def __str__(self): + """Retourne une représentation en chaîne de caractères du profil.""" + return ( + f"{self.user.first_name} {self.user.last_name} " + f"({self.departement.nom_departement})" + ) diff --git a/authentification/templates/authentification/login.html b/authentification/templates/authentification/login.html new file mode 100644 index 0000000..94549db --- /dev/null +++ b/authentification/templates/authentification/login.html @@ -0,0 +1,40 @@ +{% load static %} + + + + + + + Connexion: SGL + + +
+
+
+ {% if messages %} + {% for message in messages %} +
{{ message }}
+ {% endfor %} + {% endif %} + +
+

Connexion

+
+
+ {% csrf_token %} +
+ + +
+
+ + +
+ + +
+
+
+
+ + \ No newline at end of file diff --git a/authentification/templatetags/__init__.py b/authentification/templatetags/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/authentification/templatetags/__pycache__/__init__.cpython-310.pyc b/authentification/templatetags/__pycache__/__init__.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..449d462b9dca0f503e0621cc0c7806e1fbfede4b GIT binary patch literal 161 zcmd1j<>g`kf_oX_nIQTxh(HF6K#l_t7qb9~6oz01O-8?!3`HPe1o6v7KO;XkRlhjD zC^bhvCqF&2xFoZ%G*v&?-A6yMv?L=nuOu@qGdZy&Ge1wiBsI4nC$S{8Br&~MKR!M) eFS8^*Uaz3?7Kcr4eoARhsvXGmVkRKL!T>P{wB#AY&>+I)f&o-%5reCLr%KNa|LAvsFxJacWU< zj7LC>OKNd;Nq#|0Nl|`GPJVi3aY<%jX=+TcyH8AdDv*<(7hjf|k(peYlNwW!np=>Q ySdvo_hBx z{+X(W!h%rndw}!OqA~8fd!W0xZyVQbQ8 z3*gzLUQ=qJRxB2!v$;yEP!n{gLbsT>h{6_)cu4D^4|jvhHlyzLKJ^)puvxoeXTfp1 z&S?79$nypL>#N{W>qchIJW)$hd<>?j2Z(uax2R9XAJ-n%dZh453QwzDQs|PU9x1(& z(mN@4jdBb!bYPp(JURE8e#q6o$kF}ahQ18p|#!!Phh(Z vJ_!`V5sToyb&T-`%J<1skL2G-{+$$Vtv=4&&)&`cXc#ZYI?^T*lyv(AoEL#Q literal 0 HcmV?d00001 diff --git a/authentification/templatetags/__pycache__/sorel.cpython-313.pyc b/authentification/templatetags/__pycache__/sorel.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..d61d709ca6227bbb381dae21fe0bb7ec16f4e02d GIT binary patch literal 591 zcmZ8d&r8EF6i(V&t8s{W5FEpyUJBxE_!BP*iocMSc?yiGv37RrOgeG5c@j^ayn7Y@ znW=|CKp1%Prt}~1rC0`gkoUeX-7M7@4hK=TPaNaGmOo)mJj)YBPP$kgwauw~}lut(essp%=5WtgRAM6CGA^4Cx7# zkpp!w9OW2@GIsGQc7_JFfo3BvAX__v#zx(%Fx7KJGG(mTd={6HranztOk7yYAa5lJZGV1OeP@e&b>XjRI8Jsmk zMzgoZo-e3~I185=Eje=OiAvgqk3j=9yO@X6Mm;kAxc;!-C51OqcwXy}LWeAMN$HK0 zKFD&%SWdu(j%-t!=T)!nM_hf096kt6xyM`5;!F+1I3I@n^!69Ta|#n>v^HwdISjVR vCxK#EViD4hjxqj3`5u|-lKeZ#e~?1k>fw?5*}K_a4dazWN7_V+(%b$3eKLO^ literal 0 HcmV?d00001 diff --git a/authentification/templatetags/__pycache__/tags_personnaliser.cpython-310.pyc b/authentification/templatetags/__pycache__/tags_personnaliser.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..4953c1ef2859def1c8bff1362f60374d63248d8a GIT binary patch literal 815 zcmZ8eJ#Q015Z#aaiepE?60#`x0d8_N5<*B6P(&6|8sx^>c*o~G?u*?sBGS2nHvb_h z`5F9;ZK-G}shC*@lw_rw+j%?tX5QO&G8r*kKR&!Lza?WoDY?H8W3TaZ6g1PkVl`iK zPJ2;_S}rALz;B{kwu~Vz6D@W0jeX_IG-R<(LYC?Dg3YsE$in8_XFb$irFy`9`rfu1 zQ^8u$;oYJ=^?rk&n_?JP$x1$O&9C{5xMj#D7I-^qR1I_Klft&U&iMqXdayo$FUIw5 zE_}3en2*BwimJaeOQQcQ@@-o~?pg~~UbO|*n@>B)FW#Q#YS(X}>CMKhRd3oR|2J^2 z3YSw@bzoiFG^#Slf7V_3qpfnQ&?cp+Ny1dvG5#J%ixK!Q?HwiuY4&+9N?Asfk;uIm zL>cd8K$Aggam}@S#`e*`%XEl7qXpq+M)^m9hD2nDFdE~rhE7==8b#O%Hklv!v^yB> zPuE-6tnOFPJU(qNOIY{L%L00Pf{;xDP6n=wKJdgg3!sKtH5&Xlklj&-TYhFV+7p_& z2W`mq;JrO2jwfn^{%%zPSQXfwBJ9YqOq}wBPx(lka63a_fdUd;s-|cyIqPSSpXjV^ zHB`!Z0Vm+ZE5I8#^boWHsS+n{DR}{Aoti{Zfss8sJ3I5u?)aN&jvK-x*+eq-ki%@G3*mG1w8mzsf zaf==*;sVZNE!LxkZS1KabxjKHLt2mAi; zyu__Ne#LZ}-MKKM7vap)FE8pBiFeO;tGZ8Jz3f`xYu~RCy>RKeZq)o$;`sK8y=?fl z>*&$5eZ%r}&Pr84aUI7f+kls?K4g8XhF1zh(m{wO!|$C0wu$zXp`F?7*@lv;E2%d# zfszW8Y(tr@E7QBm*+4qm0yA`Y8qec@q_I2k90KT6dqKt$LU(yFLek=q)LFH@jvPsc zmx~w15sHEqHf?0vULEm2QFtzTs3;bMJT8d5){a!f+L0au*cPQ(;1hpqpreO)9Evk@ znWJPR-Z+A70#{5@H7FDm3QRdprjN&o&y#$$E0~z4@{Hp&TS9gXHYffv+QK zVJh+uCC@j-3`=Spxy|yn|1Y8kQm<^8rj*{-U!rueJCF!@?W8A z=eFl|=C|ixTCd$#Ze2MONM|T7)&k@#Zmt=Qe-xoj%L;VKoryk<~ literal 0 HcmV?d00001 diff --git a/authentification/templatetags/tags_personnaliser.py b/authentification/templatetags/tags_personnaliser.py new file mode 100644 index 0000000..63f164f --- /dev/null +++ b/authentification/templatetags/tags_personnaliser.py @@ -0,0 +1,29 @@ +from django import template +from authentification.models import Profile + +register = template.Library() + + +@register.filter +def has_group(user, group_name): + return user.groups.filter(name=group_name).exists() + + +# On recupère l'utilisateur et le produit +## Si l'utilisateur n'est pas le chef d'un département, afficher simplement ses demandes +## Si l'utilisateur est un chef de département +### Afficher la liste de ses demandes +### Verifier pour chaque demande que l'utilisateur appartient à son departement +#### Si oui, afficher le produit +#### Si non, ne pas afficher le produit + + +@register.filter +def affichage_demande(user, demande): + if user.profile.chef_departement: + chef_profile = Profile.objects.get(id=user.profile) + departement = chef_profile.departement + ids_profils_departement = Profile.objects.filter(departement=departement)["id"] + + return demande.user_id in ids_profils_departement + return user.profile.id == demande.user_id diff --git a/authentification/tests.py b/authentification/tests.py new file mode 100644 index 0000000..de8bdc0 --- /dev/null +++ b/authentification/tests.py @@ -0,0 +1,3 @@ +from django.test import TestCase + +# Create your tests here. diff --git a/authentification/urls.py b/authentification/urls.py new file mode 100644 index 0000000..9e4a561 --- /dev/null +++ b/authentification/urls.py @@ -0,0 +1,11 @@ +"""Routes pour l'authentification des utilisateurs.""" + +from django.urls import path +from . import views + +app_name = "authentification" + +urlpatterns = [ + path("connexion", views.connexion, name="login"), + path("deconnexion", views.deconnexion, name="deconnexion"), +] diff --git a/authentification/views.py b/authentification/views.py new file mode 100644 index 0000000..b11b2d9 --- /dev/null +++ b/authentification/views.py @@ -0,0 +1,34 @@ +"""Vues pour l'authentification des utilisateurs.""" + +from django.shortcuts import render, redirect +from django.contrib.auth import authenticate, login, logout +from django.contrib import messages + +from SGL.views import index + + +def connexion(request): + """Gérez la connexion des utilisateurs.""" + authentification_echoue = False + if request.method == "POST": + username = request.POST["username"] + password = request.POST["password"] + + user = authenticate(username=username, password=password) + + if user is not None: + login(request, user) + return redirect(index) + messages.error(request, "Nom d'utilisateur ou mot de passe incorrect.") + + return render( + request, + "authentification/login.html", + {"authentification_echoue": authentification_echoue}, + ) + + +def deconnexion(request): + """Gérez la déconnexion des utilisateurs.""" + logout(request) + return redirect("authentification:login") diff --git a/gestion_fournisseur/__init__.py b/gestion_fournisseur/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/gestion_fournisseur/__pycache__/__init__.cpython-310.pyc b/gestion_fournisseur/__pycache__/__init__.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..4a047fd3f24009fff96227778a869b05d6a92283 GIT binary patch literal 151 zcmd1j<>g`kf@jNbXMpI(AOaaM0yz#qT+9L_QW%06G#UL?G8BP?5yUSm{fzwFRQ=-o zqSPGyoc#36;*!k5(p3FmcOU)qR3IlmFFq~5v?wpLxHz@6NIyP4GcU6wK3=b&@)n0p TZhlH>PO2Tq%wi@W!NLFl?lmMh literal 0 HcmV?d00001 diff --git a/gestion_fournisseur/__pycache__/__init__.cpython-313.pyc b/gestion_fournisseur/__pycache__/__init__.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..c7884b45d22210fd0b1fa2c0d0a50eb129c08970 GIT binary patch literal 173 zcmey&%ge<81kaY=&H&MmK?DpiLK&Y~fQ+dO=?t2Tek&P@n1H;`AgNnE&Q>v@#i>Qb zF(Lk;L9Pk`&M_{j#n~nK1u-Q>`7t^9>6yhPnT4gPF~ROWG3lv5PJUi|T7GF!US@G| vYH3kSe0*kJW=VX!UP0w84x8Nkl+v73yCPPg;ULS4L5z>gjEsy$%s>_ZkLxZQ literal 0 HcmV?d00001 diff --git a/gestion_fournisseur/__pycache__/admin.cpython-310.pyc b/gestion_fournisseur/__pycache__/admin.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..e0ef450a6f436188ac6ca984c329902f3e33217a GIT binary patch literal 192 zcmd1j<>g`kf|Z??nf^ffF^Gc(44TX@fuanW zjJH@5Q*tx&{4|+v@ug%X=B4NBCFkdr6lEqAfecv5P{abHz{D?e{fzwFRQ=-oqSPGy zoc#36;*!k5(p3FmcOU)qR3IlmFFq~5v?wpLxHz@6NFQvnUP0w84x8Nkl+v73J4T>c J#UOJ97yz$uFC+i} literal 0 HcmV?d00001 diff --git a/gestion_fournisseur/__pycache__/admin.cpython-313.pyc b/gestion_fournisseur/__pycache__/admin.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..45efc1a35a800aa038aa7ddf61b002d215752d0d GIT binary patch literal 211 zcmey&%ge<81S>l&GyQ?|V-N=hn4pZ$0zk%8hG2$ZMsEf$#v(=qhIA%P=9eI8O~zZS zi7C06d48HqxA;=B67$mY^^)`RN{TX*ikN{4Rx*4Bsk`OuY!wq)oLW>I;}Hni>=A?h})q3gqPH#i!+$7Ug9Y7pImM#egl)E2zB1VUwGm eQks)$SHuA{lM#rEL5vT~jEs!;7!-=wfE)nfTR0p5 literal 0 HcmV?d00001 diff --git a/gestion_fournisseur/__pycache__/apps.cpython-310.pyc b/gestion_fournisseur/__pycache__/apps.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..cd1680a84b753fd3696c3ed92eb9a47fd08d17d7 GIT binary patch literal 455 zcmZuty-ve05VqqKh5jtifdz>*OR^ybgj$f=1$CfX7AtU0FgS4<*8{BZGM#uIuS~oG z6X&KzNb^+-cbXd9g<>;+~5*uk%W9?)sb~&?@f_ zIbYda?J6fAirlI-&ykK7TfWfOHl+1O+M3_X^jTLTHM$ilRl1b8=*o(8IloW;8J^}% zW0K~rWys)k literal 0 HcmV?d00001 diff --git a/gestion_fournisseur/__pycache__/apps.cpython-313.pyc b/gestion_fournisseur/__pycache__/apps.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..85c51e4c4ae7c16ab199f1b944fb0718f8c9d65f GIT binary patch literal 556 zcmZuuO-md>5bd6sU02N#jftov;N}pR%iaVL5&S?!MS@Lk4aMm64(-lPkJUW~a~1pt z3;qR9{*@f1Atz7Xgw?y<&Ppz+L)9x@y{@XRQM)}wob^vu<(-QUK6$ss7>s^6FeHpH zdPoi^(q*zhz7rNK5f*Z~64rGXWKrCB^hr$Z&mgf>zYyQ;!MYAq_PUwn+5`1iN;JSj5OO;5W6m5N+)<%wBJ#!d3xGC>k!O$?gYvX8LIYsS%{cPg+O6$1{!0tgeE%ok5xQ?w$qg!= zt4z8LFDk*=-Vy)Lz&t5S-7PQC-{Q^r)pgssYjVH1`X`#dpI*M&!I^jdI1cUf_-DKr t{dH=&pQtXJb;!2X>)khS&ZYh^`m=LSA*J*$={z?B+PS%WAuhbBUIC4Sn9%?L literal 0 HcmV?d00001 diff --git a/gestion_fournisseur/__pycache__/forms.cpython-310.pyc b/gestion_fournisseur/__pycache__/forms.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..cc927b3eecb563135e3e679c26a0539166595a2e GIT binary patch literal 1124 zcmb7D&2G~`5cb+@$N6ar6)FNGlpD%{MCAfP2=ziMB+^Sc`C?h#N$P6tb$4x1axGWh zfCnINz&&rVS57#{?55FFsf=v|B`4B{X5n?*s<*gP!%3?BuDya{U z&TPG^5}}G>z4~2qX!W6;S>rhl?XXaJ3`M1()R_T$o6e;MdXWwc8k3^3;an9dHP3b{ zkWikf0;~^tl1bZ5lL{6}XJENb)77Fh`aTQ-zl(Nj*-gN}FZBQ5%ev zR^veXn1BulIs{Z_-6f#0JsA&d7{^7DLmb;)9AmF)N%A0$FX}{YEuAWltQ>uZNDzE`JUvr6 zOpVeYr&2949OjD}rl-fRrrXJm=htI9r3B5Sd}}$ii1ILZ5kiME?s7Kla~3fEW9SVT zK5p-;zK7NgpEJ6X`ox`qJ7D|XPgFlGoB#j- literal 0 HcmV?d00001 diff --git a/gestion_fournisseur/__pycache__/forms.cpython-313.pyc b/gestion_fournisseur/__pycache__/forms.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..f3bca75e00789f819a9bb0b2078e3452c13c5b3e GIT binary patch literal 1517 zcmcgs&u_Mj=FQHV_r5pp zn;p%}6bU>J|G47q>V*7)lcUEN8>2Nao)C+0Vrf?9rnZ*hnFiX~o7pv;>kU#Rr-`M{ z6U(qOx08rRLDKPZHXXUyGn={ieVDE6ZF9EK@R?|IL*9>l$Kzl}Vayx8)95iFy)bBW zlJ%Geo)9eNqIH0gnwm0jmjGjG8Mcg<-84;#P*3uV7GZcoY{E6DA!BJgYh}2eaLxi} z{coLD0I9@1KxWgXG8$lFHRlJV% zq;|a8SdQM4F;Fm!}|LExy7Fz{rG5quKq)5Fni%uHgmpoXp&m} zX?e4}^{sTWSI$1GoZY&&6ATuw4=c+rYxU=~ zrDwGzh~6Jux;3n|U!5qPD1MXUr-2PWgMd}9H**|?%;ylQ2sMOxgv9F|w9qx(`7T=K z5#UcjV5^}%{o?O>)hNCp0I4s!VFC=M%+BXd076UpHhXk_5eF@JvX%5!q>V1LvC*jV zG|}71RsO?NKUevAh^xUX>HvpXP19bGtG|-!&!qLnJf#)CW#5P2g})In6GDFi;)REc literal 0 HcmV?d00001 diff --git a/gestion_fournisseur/__pycache__/models.cpython-310.pyc b/gestion_fournisseur/__pycache__/models.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..30d2abb911d4e7b1b7c6fb0bac80a78494222676 GIT binary patch literal 340 zcmYjN!Ab)$5Y6`Dve17B-g?jUGH)h%FE3%a>;%X4_bq<#{yBkpGz{)}QOn7SM`4?tSS|89!%Zy_UZn$)$6)K* zRE!}<=>~ZKN*KJf+}m@{BN60Ceb;U0=WQ)}OhFfbTRb^}IW<%d;szS7zTqjeE+!4@v*>qb3= oBPa?HoO0oS{PyPzYPZ>{Un6>ELj9|s+dHnagZ1=JG%>c~2j;PGUjP6A literal 0 HcmV?d00001 diff --git a/gestion_fournisseur/__pycache__/models.cpython-313.pyc b/gestion_fournisseur/__pycache__/models.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..772e7ece8ded8e5f50483cce62f3af9ea85b5435 GIT binary patch literal 361 zcmYjNO-chX6rR*U%RuiC+;uYtDB{LKT@(?DyFeI{*C7}uV}1&H5AR@h-XTYDH(M_t z&RX!Lw9>c9_r2tOU%ofaW>tZ8`MXe`cz$JaEOG$j6v11uDQwY_`6PTGU8QK@m1=PG z$;kAcL2rVkx}hyNuS`cJ_O{sTlyeZQtE*~#`d+5ERd`92P}Fpursz|o*zR>BQgn0& z)*a<|Z;cGf*XRe@)%{DgH%xJ-JfJa3=TYcn(+MO(SrK%jETHqgJc7}A+EnO}mWH5qSl zgrpXiI42gT`e`!V;!ep*%uCPLD*=iXF#{E>WcUnHcgxw?DkiizwWv78BOt~lwK%&Z zzaXZhC_g4AKRvU!B(tzIH73~ICng=JF*83eJ}tkrC@-_PIJLAW24q;VUP0w84x8Nk fl+v73yCM#tnT$YO3}Sp>W@Kc%$DmNe2IK$$lu|hq literal 0 HcmV?d00001 diff --git a/gestion_fournisseur/__pycache__/urls.cpython-310.pyc b/gestion_fournisseur/__pycache__/urls.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..35d3a1ed34d94e21efb114f363b55599d3119630 GIT binary patch literal 872 zcmaiy&2H2%5XYUb-E_0tuSMd(B?k_y#BMloSXC9bUMdb$Tylx5j!C_8;>Au1L_9z* zJV>7diHGo&Qzf1NfndBFDhmok^29&S|L;u3mXpbd;PdI*l3xXce74{|Hv0^Revbi2 zPQU|Sc$J^~9)SQt5maFw;ylVD=EH!6s{srl{tzJTAPr&EQ-T!3xTguy4(#@{hctry zo(_-_IJ8s_@-a-$$n0MG1WP#ic&%8M3Z~PSFHY07Y*i{~S~A^mS*L*OuW+sATC-N^ z#SMDM%roJdHWxSE7NSee-e@!JU4`Q?#6-LX_SSl8TCwgxaNV%EtJyBOw(h|ns`)u> zSSb}}W}9^N#ci^CxOEDCsVLX7&W?E9EIGLH<8JRaRrd&3L%GmyVRu^1v{$+tc8@Er z*__T-*sT9<(cS-x`uS{PhD8DLyeLcpD_WOw(JG;pkDXQn8$t{wrt5WK+o^^Y4>y0~ z7NnKEX}>yk+YDEt606vhQqaN{?q*Gb-^D|2n5y+PQBxFe!q=zSg{)YnrD7rzvc%)$ zuUnR#ot$QO+4A9W3oS(*^BG zZ+P-#!e3y*-(lj}J+Vw;Vq!dSW3wJTIPKEy1ToHG=FR(l-s_v!*VXkwAl8@Pi)23w zz>nyXtiqYm{UwZ#009b+f--B$YKCSEfU-zk%dV9XihEpZ6&|se^2x2txrzaZf6S^RZsghV|xKE4-Vm$GuCmQV&V}iJxDv5=P5iyse zL-kU5ym?pnS3Vz792zcWMr~u=X!uQPxVBNpEFivTIKuy2_&mZGZcpX8+j=yDDyx?rxUfr)YsmrLCUqJKGriqP1yV0|ymmTg6a%PKF3?~0!sVCu0$&=oA;4<0U>HHIlOA3rl6VfHfc8)iU# z)Aj4(uaZ|yY@(HQ^MXMzqi0kbZ#Z1q@tvlNm+6E^8BGxTB(~G6qA15;;U~EI4V1nY zjJL3p1KPlTaliIq^Zn+*UQ4}stim>&Jg6N_&9|oJzb-xPWHVYW=Gt(!4fP{fZozU} xzun2JLKqYY+OR4K*JR;dEKIlHbX%X1g@ss{ZHb)vjaWD>Um3}~E6_`#)IZU!M5X`$ literal 0 HcmV?d00001 diff --git a/gestion_fournisseur/__pycache__/views.cpython-310.pyc b/gestion_fournisseur/__pycache__/views.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..68010e10a8d1da4037fa53e40609a1d592e1683e GIT binary patch literal 4934 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 literal 0 HcmV?d00001 diff --git a/gestion_fournisseur/admin.py b/gestion_fournisseur/admin.py new file mode 100644 index 0000000..cced46a --- /dev/null +++ b/gestion_fournisseur/admin.py @@ -0,0 +1,3 @@ +from django.contrib import admin # noqa: F401 + +# Register your models here. diff --git a/gestion_fournisseur/apps.py b/gestion_fournisseur/apps.py new file mode 100644 index 0000000..890fd65 --- /dev/null +++ b/gestion_fournisseur/apps.py @@ -0,0 +1,6 @@ +from django.apps import AppConfig + + +class GestionFournisseurConfig(AppConfig): + default_auto_field = "django.db.models.BigAutoField" + name = "gestion_fournisseur" diff --git a/gestion_fournisseur/forms.py b/gestion_fournisseur/forms.py new file mode 100644 index 0000000..352358f --- /dev/null +++ b/gestion_fournisseur/forms.py @@ -0,0 +1,34 @@ +"""Gérez les formulaires pour la gestion des fournisseurs.""" + +from django import forms +from gestion_produit.models import Fournisseur + + +class FournisseurForm(forms.ModelForm): + """Formulaire pour le modèle Fournisseur.""" + + class Meta: + """Métadonnées pour le formulaire FournisseurForm.""" + + model = Fournisseur + fields = ( + "nom_entreprise", + "nom_prenom_representant", + "fonction", + "telephone", + "email", + "categorie", + "rccm", + "nifp", + ) + widgets = { + "nom_entreprise": forms.TextInput(attrs={"class": "form-control"}), + "nom_prenom_representant": forms.TextInput( + attrs={"class": "form-control"} + ), + "fonction": forms.TextInput(attrs={"class": "form-control"}), + "telephone": forms.TextInput(attrs={"class": "form-control"}), + "email": forms.EmailInput(attrs={"class": "form-control"}), + # "note": forms.NumberInput(attrs={"class": "form-control"}), + "categorie": forms.SelectMultiple(attrs={"class": "form-select"}), + } diff --git a/gestion_fournisseur/migrations/__init__.py b/gestion_fournisseur/migrations/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/gestion_fournisseur/migrations/__pycache__/0001_initial.cpython-313.pyc b/gestion_fournisseur/migrations/__pycache__/0001_initial.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..ae74cc48662e40b17205d6799ab0f00da6458e9b GIT binary patch literal 1876 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 literal 0 HcmV?d00001 diff --git a/gestion_fournisseur/migrations/__pycache__/0002_remove_fournisseur_categorie_fournisseur_categorie.cpython-313.pyc b/gestion_fournisseur/migrations/__pycache__/0002_remove_fournisseur_categorie_fournisseur_categorie.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..82e7992fcb77e55ed44f56a462d5848baf6ce7f7 GIT binary patch literal 1068 zcmZ`%&rcIU6rSB}m+iJ#C>l`+R>OftgVn@Dj3F_oBo)wffzu|Fr8_OF+nq8qOM)j7 z6V6^Zd*<)(9{?^ibM?fnq#AF=H@g&w!A<7v`#s-$@AZd=Z3N$D^Uvlt9ibn}7<}1t zr9ThKK5~$wy+bvPX*HecWi*Z+AV=Ah{E|IA2rX0$Su?5Q#;y0qIti+LiT z5tnA0`XuCy%Nm3dIN<2-g4jncVw!`P?r6+#bjNtCvy7Xq7p|71I)KSIS;w5yA%5e3 zao4Jsu8j>jmXn*)9eYmQVLN%2Zxt%TGPgXyd#c_DFBoePuJGd~jad|MPGTkt)oS$# z4x&H=UI+k@>5wa}7vpQ5KMd zK1CUhyf%>;B|qQ!=cd_<^mq~gFL>hnK~i1zN%XZQNr%8oqeehD zQwt&Ub<(EWmR|kzR*uCC6+u31iPZFUNz7Ap!^-PqjcCA`3Yuq$fgc5Z$#CH+EAIQV<2TBC2}HrBomeMNm|g52=)b;`U~`a^k6DaJ=cPjo^la z#F=|=f?cPfJ!B=X=gsWQ&b((2rluUC7JmKH{!0n@uEA&( z&y2x}GWLl}T>6ZxQ>5z#8Z|OQ=80?EAg<}rhBZn$f8RBSHkx6fUOd&HZb+vSh3Kad zPlU8OJb+lV&T|N{&%j_u8T-T|NL_-4OVM!24O^m1n{$Z7~(Jm?8XQa?#^ z-u!ngh9peeviugX$px^)??ByDoN69(Bn#Rni@OoTL62;z8A~jWFeV+QdI_=^lwD?Q zFY{x4TA@pf?M5ilI7%SlIvhY3k^quc1Ol~^(plB>KhcG;pdI#F+aF@-@Ggv0y~>zK zmBKCNrzu9wECsX+u0v+b7buhz+!F8dt0j8-0h^)5oQ`qte{T zwS|+*vnSP=5PHR@M5rj#{p~-e$cZ?clYagnTh*<}~Hh z3~$sE56{jiOP1~r$zQ>n3aX!t2wkXeQc8bYgw}srWomtPjw=g?m4#nKfjs*kY8eOd literal 0 HcmV?d00001 diff --git a/gestion_fournisseur/migrations/__pycache__/__init__.cpython-310.pyc b/gestion_fournisseur/migrations/__pycache__/__init__.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..2e007aa3e799ae1dc62d87b6951d4e5218be33ec GIT binary patch literal 162 zcmd1j<>g`kf@jNbXMpI(AOaaM0yz#qT+9L_QW%06G#UL?G8BP?5yUT7{fzwFRQ=-o zqSPGyoc#36;*!k5(p3FmcOU)qR3IlmFFq~5v?wpLxHz@6NIy3-y(keRTC5)*pP83g c5+AQuPv@#i>Qb zF(Lk;L9Pk`&M_{j#n~nK1u-Q>`7t^9>6yhPnT4gPF~ROWG3lv5PJUi|T7GF!US@G| zYH3kSZf1H>B1p72CO$qhFS8^*Uaz3?7Kcr4eoARhs$CH)&>oOGib0Hz%#4hTMa)1J E00&tzzW@LL literal 0 HcmV?d00001 diff --git a/gestion_fournisseur/models.py b/gestion_fournisseur/models.py new file mode 100644 index 0000000..b7689e2 --- /dev/null +++ b/gestion_fournisseur/models.py @@ -0,0 +1,7 @@ +"""Gérez les modèles pour la gestion des fournisseurs. + +Les modèles définis ici ont été déplacés vers gestion_produit.models.py +pour éviter les dépendances circulaires. +""" + +# Create your models here. diff --git a/gestion_fournisseur/templates/gestion_fournisseur/details_fournisseur.html b/gestion_fournisseur/templates/gestion_fournisseur/details_fournisseur.html new file mode 100644 index 0000000..b4fef59 --- /dev/null +++ b/gestion_fournisseur/templates/gestion_fournisseur/details_fournisseur.html @@ -0,0 +1,82 @@ +{% extends "BASE.html" %} +{% load static %} +{% load tags_personnaliser %} + +{% block page_titre %} SGL - Gestion des fournisseurs {% endblock %} + +{% block "contenu" %} + +

Détails du fournisseur

+ +
+
+
+ {% csrf_token %} +
+ + {{ fournisseurForm.nom_entreprise }} +
+
+ + {{ fournisseurForm.nom_prenom_representant }} +
+
+ + {{ fournisseurForm.fonction }} +
+
+ + {{ fournisseurForm.telephone }} +
+
+ + {{ fournisseurForm.email }} +
+
+ + {{ fournisseurForm.categorie }} +
+
+ +
+ Actuellement : + {% if fournisseur.rccm %} + {{ fournisseur.rccm.name }} + {% else %} + Aucun fichier téléchargé. + {% endif %} +
+ +
+
+ +
+ Actuellement : + {% if fournisseur.rccm %} + {{ fournisseur.nifp.name }} + {% else %} + Aucun fichier téléchargé. + {% endif %} +
+ +
+ +
+
+
+ +
+

Livraison du fournisseur

+
+ + +
+
+ +
+ +{% endblock %} + +{% block "js" %} + +{% endblock %} \ No newline at end of file diff --git a/gestion_fournisseur/templates/gestion_fournisseur/index.html b/gestion_fournisseur/templates/gestion_fournisseur/index.html new file mode 100644 index 0000000..a272712 --- /dev/null +++ b/gestion_fournisseur/templates/gestion_fournisseur/index.html @@ -0,0 +1,64 @@ +{% extends "BASE.html" %} +{% load static %} +{% load tags_personnaliser %} + +{% block page_titre %} SGL - Gestion des fournisseurs {% endblock %} + +{% block "contenu" %} + +
+
+

LISTE DES FOURNISSEURS

+ {% if user|has_group:"Logisticien" %} + + {% endif %} +
+
+ +
+
+ +
+
+ +
+
+ +
+ + + + + +{% endblock %} + +{% block "js" %} + +{% endblock %} \ No newline at end of file diff --git a/gestion_fournisseur/tests.py b/gestion_fournisseur/tests.py new file mode 100644 index 0000000..5ed216e --- /dev/null +++ b/gestion_fournisseur/tests.py @@ -0,0 +1,3 @@ +from django.test import TestCase # noqa: F401 + +# Create your tests here. diff --git a/gestion_fournisseur/urls.py b/gestion_fournisseur/urls.py new file mode 100644 index 0000000..27f1f0e --- /dev/null +++ b/gestion_fournisseur/urls.py @@ -0,0 +1,33 @@ +"""Gérez les URL pour la gestion des fournisseurs.""" + +from django.urls import path +from . import views + +app_name = "gestion_fournisseur" + +urlpatterns = [ + path("", views.index, name="index"), + path( + "liste-fournisseur", views.liste_fournisseurs, name="liste_fournisseur" + ), + path( + "liste-fournisseur-categorie", + views.liste_fournisseur_categorie, + name="liste_fournisseur_categorie", + ), + path( + "liste-livraison/", + views.liste_livraison_fournisseur, + name="liste-livraison", + ), + path( + "details-fournisseur/", + views.details_fournisseur, + name="details_fournisseur", + ), + path( + "mise-a-jour-fournisseur/", + views.mise_a_jour_fournisseur, + name="mise-a-jour-fournisseur", + ), +] diff --git a/gestion_fournisseur/views.py b/gestion_fournisseur/views.py new file mode 100644 index 0000000..93f4fd4 --- /dev/null +++ b/gestion_fournisseur/views.py @@ -0,0 +1,195 @@ +"""Vuews pour la gestion des fournisseurs.""" + +from django.shortcuts import render, redirect +from gestion_produit.models import Fournisseur, Categorie, Commander +from django.http import JsonResponse +from django.contrib.auth.decorators import login_required + +from .forms import FournisseurForm + + +@login_required(login_url="login") +def index(request): + """Gérez la vue index de la gestion des fournisseurs. + + Parameters + ---------- + request : HttpRequest + La requête HTTP entrante. + + Returns + ------- + HttpResponse + La réponse HTTP avec le formulaire de fournisseur. + + """ + if request.method == "POST": + form = FournisseurForm(request.POST, request.FILES) + if form.is_valid(): + form.save() + + form = FournisseurForm() + return render( + request, + "gestion_fournisseur/index.html", + {"form": form, "listeCategorie": Categorie.objects.all()}, + ) + + +@login_required(login_url="login") +def liste_fournisseurs(request): # noqa: ARG001 + """Renvoyez la liste des fournisseurs au format JSON. + + Parameters + ---------- + request : HttpRequest + La requête HTTP entrante. + + Returns + ------- + JsonResponse + La réponse JSON contenant la liste des fournisseurs. + + """ + fournisseurs = Fournisseur.objects.all().order_by("-id") + data = [ + { + "id": f.id, + "nom_entreprise": f.nom_entreprise, + "representant": f.nom_prenom_representant, + "fonction": f.fonction, + "telephone": f.telephone, + "email": f.email, + "note": f.note, + } + for f in fournisseurs + ] + + return JsonResponse(data, safe=False) + + +@login_required(login_url="login") +def liste_fournisseur_categorie(request): + """Renvoyez la liste des fournisseurs par catégorie au format JSON. + + Parameters + ---------- + request : HttpRequest + La requête HTTP entrante. + + Returns + ------- + JsonResponse + La réponse JSON contenant la liste des fournisseurs filtrés par + catégorie. + + """ + categorie = Categorie.objects.get(id=request.GET["c"]) + fournisseur_categorie = Fournisseur.objects.filter(categorie=categorie) + + data = [ + { + "id": f.id, + "nom_entreprise": f.nom_entreprise, + "representant": f.nom_prenom_representant, + "fonction": f.fonction, + "telephone": f.telephone, + "email": f.email, + "note": f.note, + } + for f in fournisseur_categorie + ] + + return JsonResponse(data, safe=False) + + +@login_required(login_url="login") +def details_fournisseur(request, id_fournisseur): + """Affichez les détails d'un fournisseur spécifique. + + Parameters + ---------- + request : HttpRequest + La requête HTTP entrante. + id_fournisseur : int + L'identifiant du fournisseur. + + Returns + ------- + HttpResponse + La réponse HTTP avec les détails du fournisseur. + + """ + fournisseur = Fournisseur.objects.get(id=id_fournisseur) + fournisseur_form = FournisseurForm(instance=fournisseur) + return render( + request, + "gestion_fournisseur/details_fournisseur.html", + { + "fournisseur": fournisseur, + "fournisseurForm": fournisseur_form, + "id_fournisseur": id_fournisseur, + }, + ) + + +def mise_a_jour_fournisseur(request, id_fournisseur): + """Mettez à jour les informations d'un fournisseur spécifique. + + Parameters + ---------- + request : HttpRequest + La requête HTTP entrante. + id_fournisseur : int + L'identifiant du fournisseur. + + Returns + ------- + HttpResponse + La réponse HTTP redirigeant vers les détails du fournisseur. + + """ + fournisseur = Fournisseur.objects.get(id=id_fournisseur) + if request.method == "POST": + form = FournisseurForm( + request.POST, + request.FILES, + instance=fournisseur + ) + if form.is_valid(): + form.save() + return redirect( + "gestion_fournisseur:details_fournisseur", + id_fournisseur=id_fournisseur + ) + + +def liste_livraison_fournisseur(request, id_fournisseur): # noqa: ARG001 + """Renvoyez la liste des livraisons d'un fournisseur au format JSON. + + Parameters + ---------- + request : HttpRequest + La requête HTTP entrante. + id_fournisseur : int + L'identifiant du fournisseur. + + Returns + ------- + JsonResponse + La réponse JSON contenant la liste des livraisons du fournisseur. + + """ + commande_fournisseur = [ + { + "date": c.date_livraison, + "produit": c.produit.libelle, + "prix_achat": c.prix_achat, + "quantite": c.quantite_commander, + "montant_total": c.quantite_commander * c.prix_achat, + "date_livraison": c.date_livraison, + "statut": c.livrer, + } + for c in Commander.objects.filter(fournisseur__id=id_fournisseur) + ] + return JsonResponse(commande_fournisseur, safe=False) diff --git a/gestion_produit/__init__.py b/gestion_produit/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/gestion_produit/__pycache__/__init__.cpython-310.pyc b/gestion_produit/__pycache__/__init__.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..d49e21ba0a18bd1d7373bda8ab214f87de128048 GIT binary patch literal 147 zcmd1j<>g`kf_IB=Wq|0%AOaaM0yz#qT+9L_QW%06G#UL?G8BP?5yUSu{fzwFRQ=-o zqSPGyoc#36;*!k5(p3FmcOU)qR3IlmFTS8CKczIYL_a=0GcU6wK3=b&@)n0pE>JKh O)edA{F%ytrVE_P1QzCf) literal 0 HcmV?d00001 diff --git a/gestion_produit/__pycache__/__init__.cpython-313.pyc b/gestion_produit/__pycache__/__init__.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..701ff278ee7ec1a26970db8f283b345482f87678 GIT binary patch literal 169 zcmey&%ge<81n(B#$^g-iK?DpiLK&Y~fQ+dO=?t2Tek&P@n1H;`AgNm(&Q>v@#i>Qb zF(Lk;L9Pk`&M_{j#n~nK1u-Q>`7t^9>6yhPnT4gPF~ROWG3lv5PJUi|K~a86X=X`G qe0*kJW=VX!UP0w84x3z{U{0!C5i8JOkj2Fy#z$sGM#ds$APWGs$}C&} literal 0 HcmV?d00001 diff --git a/gestion_produit/__pycache__/admin.cpython-310.pyc b/gestion_produit/__pycache__/admin.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..903aff5750149983a14776ae0eadbcbae7afc9bc GIT binary patch literal 188 zcmd1j<>g`k0?97ROn)H#7{oyaOhAqU5Elyoi4=wu#vF!R#wbQch7_h?22JLdKv4!w z##^k3DY=<>ews|T_)@YG^V0M6lJoOQiZYXmKnAR2C}IIpVB(jtenx(7s(x{PQEHBU zPJVi3aY<%jX{vs(yN`Z)Dv*<(7hh16pHiAxq7ODzub}c4hfOX}Bq!C55ok^^$V>qS E0D5&S(*OVf literal 0 HcmV?d00001 diff --git a/gestion_produit/__pycache__/admin.cpython-313.pyc b/gestion_produit/__pycache__/admin.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..2d0295725c58f2a782c219b8dba284a0fba4e86c GIT binary patch literal 207 zcmey&%ge<81d?5rnf^ffF^B^LOi;#W0U%>4Loh=yqc?*WV-ceQLpqZt^GlGlCgUyE z#FX63JU>mQTYM>5iFxVyddc~DB}JJ@Ma)12D;Yk6)ZMaowu%WYPAw{q@d$`4;{!7zBjY^=g(5Z}2LNriHOl}1 literal 0 HcmV?d00001 diff --git a/gestion_produit/__pycache__/apps.cpython-310.pyc b/gestion_produit/__pycache__/apps.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..6882965d225b69246c095cf3f4c352589ccbe8b6 GIT binary patch literal 443 zcmZ8dy-ve05I)B#3T+V*>WajgC6SmI5Nbi93#t&^vRHw0gTaZ@I2mAtcR{?8S0-M8 ziE~qlij(eqf8TfKGY1DlAbGw!Qy=tx`CwN<3Z|s?gbV^Q4JFGMgE?S;{2h=>_QtaS z!zILnZ|Z`Wx&2vPUzuv9iU*(B6-L37)K17q$QS~lS;jHQLgd5}y2)JHR+;LyG1#fL zXL>!xr@Sgmg7-;jP->f8s$$l)=2}UO?y%@VqV7?Pc;F%-s=Sm!xSa_RALae)7 zZ!1SAS9zyfkrS0zZMZ^T`-H|HXJdX&(??Uv)S5=>RGUK4g6mGE%lS?EZ*ZE|wN2`m wh7;N!(C(3mAY>8S5bd6sU02Owj2~!F&>RAD*_)t21fxVz5lNF;z6|Y`VAA@dpj5s^}xhn5m{Ogl9YYoBRs{=QL5k~jP z9!0uD=ExVqqR)iIoUX*74x=JTTTebosU6*{>n&CFWpNVd;OQ_KEI4pOI6=w?MvP+2 zB1~9}EtX)rXr*mCy(6@dsyafIH`0V|Pl*#=F6O_ps!+ZBxOb*?3=;ABnd@dtqOCM$=`1VCS+Hl?gYr5yb!7yYa$4P>sn z<9z$X7uy*CZ89TIATtK#abtuAz>b@5;J36JTi^IEEl~5_Bfc&4sZljIsCcOg={7rW z1ZO)3{N1oTt83k>FVNrr)%lfm*STx*Fu!`A%sz}STy5jWH~uhC7oH3vSiD#1#rZfT~f0 zT;f5*Du(*{5PUKI9oGST1^}@U+&|rHxOBQyo1^y1!4xrT-+#>3+r;h1)DiqLffB zy{B|?H^8T7KPEUEaJ~Hm4AlZ1HpL)%U_$x^F(G~PwGmjvg4Auf@^i}RJ`*{o2~G3z zM@PM1rrDRtuhF@Q9kN!WopKGmOG&t85`tVvf?9!1jKHDpp@-FBI`sSg*3KK#(6}t6v_l8A;nCEdR<4_EQ$81bYr$lIVUT`STU|K7C5Jy6sHL$4b@MzAn zcnn33@|=sax(W*#(?Q;~c>~hpK)1$QXqM0{gW2vjq!)&1l+ZAgwJ=P8nHcXIVF>xf z<%k=GBpZYw$I~Efm_=jh>@gY>!3~W0f6}A;*K}Cqvc6p;yOd8HXGi5A-It8)(_D-- z-huhboIUIxWC`tyjMKOuXNU=VUeNx|=5PHHWmvw#xUb;t4PQwMHyqEbz)klwOScS5 zZ~2z)=+?WIS$)_3-P*$4v~j{cG#{fuBsi9bKS0x&H)@-4 z|G$DuAe&VcmksaTq-y;0`DZ%lst3P>J2m(PhS0mVGRsq4tMupbP3ut#;(M!s#B9JN zUVvFtjZ0#5S(@g>=-jIj2OGz+QOekyPmE&+_bP0haE8CRirg+P~M4g*f)% z;)*Qvt|e=!YLgXMk8TJSnY7pUay4yo2aw8*xWXoPH9K`+3I1|SS!%%S`lJa0Np{dA z4IrsG`tZV{WcEx=q!Mq(cs)6m%bj6ZaJQ zt5D6BD`izj1s5p&EgVD0R8vy=#}QSI?^~p_()(f3)qlc&eggjhSX#rltGCVeYP)g! F!T)n1n7;r3 literal 0 HcmV?d00001 diff --git a/gestion_produit/__pycache__/forms.cpython-313.pyc b/gestion_produit/__pycache__/forms.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..2bedc4905d76b968d898b4ff6bee022b2344fe70 GIT binary patch literal 4069 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 Z5eLvbMj$Q*F+MOeGBVy{P$*&pasZC|H&p-t literal 0 HcmV?d00001 diff --git a/gestion_produit/__pycache__/urls.cpython-310.pyc b/gestion_produit/__pycache__/urls.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..3cf096c852240836cc3b94f902a48bfd4c989f63 GIT binary patch literal 1342 zcmb7@y>8nu5XU81j-A-@S3aD6p+-9t85{*2+aM^=0$GZpKsGOe;A0&olBkkY+G_6F z2kF+g=+qbB(4|vep+JEiL&|czMSv*%c*ncr|40@DTMj28gp#80Zw29P$O-oxyZRl9)B5guo zsfV-$eM}k-9LnG(rks+tLnF4|Xl>A@yO;(imv~V@vx;L%3(@KGFytXj%lb zZFqR*96TzIP6;RF1c;avJQ4UaNuI@dp3r$LDa$4cBJ?-PIfH`A!)sK=hx(v!4?EBC z{y5ynLA9~+NVk}`G@3rwiN&qnRb{H3S~wmp8@Jl#st^^J4n;!7vXH8G(~!z4)Oe{- zWGq#yc5kJq&YkKnCB}%TJq9q^N9%^Cb>vk|^B60x!ts&bbO(jOTOkS0#CL~3(c3Ut)_q>MZ W`Yyizyyjj1dbr}QYw9fRpZ@_CTCq+5 literal 0 HcmV?d00001 diff --git a/gestion_produit/__pycache__/urls.cpython-313.pyc b/gestion_produit/__pycache__/urls.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..46716cd6b1517eb0194d6b81020bbd34a84be4d9 GIT binary patch literal 1828 zcmZ{k&u`O66vxN;(M}tjmL_dVla#cjpdQkc!y-{oE+C3vwL(}NkStkNJOo2xduQzK zZcfXQ)1Fr1U)bCJBS`p!8EK`}t~hX`>Oa66J081H@WGyW-_N}F=Diu8tLid>=e=^r z{(AwT|HUMI)~18={}hD&L>i(pvwjzmDAU5U@ ztCF}3#O560vLx1k*qTGsBvA*VHHTQ2#0C)CbBGN|G=S*LAsUj{1Y&m%aYYhaKwO(c zGzHO9X>Hg#Xitt#2qlw_MOY`GBL;)c=!WTeBYR-_w(E3;go&@=QP&D=|L}`&d7$u; zXZkO{z%db%@~KUJVSHr<=7^VV$0EN9-Z95yvO2PvPrBfn3|(py#@C2L$q=lR&?iX@ zzLD9+#PQSEyq4MNJ$F1d!8dPY#uy%?Lf-RzlEAZ`t;9a52A%~ub>%$Cb2?=cHJML~ zz>{g3*JSfz3fcDfjAF=*Pu9k6a7skR5VXsDckp`Bpip_2`rS-Rgd<7@fd`$U-4|{^ z9h)%{&@4{xuI>28wv}eo=j%Bx7xk(|eA6CH%ORId_u239Y62Kj%TEV&zGxVhJ1`7h zv0j5##E z(+_-JjT@4xj5lP3j6_LWwSFN)dhYm&EHQY5+Jl3n_QtHRmwC?D)H5OD)E%vfO;?~W za4UR59rhPG2NUA`d&l}SMkv!CKGE+J_S$zn-KVZTa>b#ye-4PQo&2cJ+#Frh_|W@} zt~Cl z^1|72Y~BL%N4y>4?MS_v7h18f6XKmn-Omf{SlA8mZlqq%3*TL_8Lw!DxEZPKY{iGA zEAM{z*zASP-iKQc!qUm75{_^qhWA6fAE~Vjjv$=KbT7nvk$NL9ByrmzZb#})Uf9XG kx{&E{EZhw7%}BkLUvUr%tq`};OusUvzfyQpq2ibM4R5CfkpKVy literal 0 HcmV?d00001 diff --git a/gestion_produit/__pycache__/views.cpython-310.pyc b/gestion_produit/__pycache__/views.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..cd68a830ff6f770756f947a1508b04c936c65fda GIT binary patch literal 12476 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 C(5goO literal 0 HcmV?d00001 diff --git a/gestion_produit/admin.py b/gestion_produit/admin.py new file mode 100644 index 0000000..cced46a --- /dev/null +++ b/gestion_produit/admin.py @@ -0,0 +1,3 @@ +from django.contrib import admin # noqa: F401 + +# Register your models here. diff --git a/gestion_produit/apps.py b/gestion_produit/apps.py new file mode 100644 index 0000000..0115501 --- /dev/null +++ b/gestion_produit/apps.py @@ -0,0 +1,6 @@ +from django.apps import AppConfig + + +class GestionProduitConfig(AppConfig): + default_auto_field = "django.db.models.BigAutoField" + name = "gestion_produit" diff --git a/gestion_produit/forms.py b/gestion_produit/forms.py new file mode 100644 index 0000000..0d816ca --- /dev/null +++ b/gestion_produit/forms.py @@ -0,0 +1,104 @@ +"""Génération des formulaires pour la gestion des produits.""" + +from django import forms +from .models import Produit, Categorie, Commander, Demander + + +class EnregistrementProduit(forms.ModelForm): + """Formulaire pour l'enregistrement d'un produit.""" + + class Meta: + """Métadonnées du formulaire.""" + + model = Produit + fields = ( + "image", + "libelle", + "quantite_stock", + "conditionnement", + "seuil_pre_rupture", + "categorie", + ) + widgets = { + "libelle": forms.TextInput(attrs={"class": "form-control"}), + "quantite_stock": forms.NumberInput( + attrs={"class": "form-control"} + ), + "conditionnement": forms.Select(attrs={"class": "form-select"}), + "seuil_pre_rupture": forms.NumberInput( + attrs={"class": "form-control"} + ), + "categorie": forms.Select(attrs={"class": "form-select"}), + } + + +class EnregistrementCategorie(forms.ModelForm): + """Formulaire pour l'enregistrement d'une catégorie de produit.""" + + class Meta: + """Métadonnées du formulaire.""" + + model = Categorie + fields = ("categorie", ) + widgets = { + "categorie": forms.TextInput(attrs={"class": "form-control"}) + } + +class CommanderProduit(forms.ModelForm): + """Formulaire pour l'enregistrement d'une commande de produit.""" + + class Meta: + """Métadonnées du formulaire.""" + + model = Commander + fields = ( + "produit", + "fournisseur", + "quantite_commander", + "prix_achat", + "date_commande", + "date_livraison", + ) + widgets = { + "produit": forms.Select(attrs={"class": "form-select"}), + "fournisseur": forms.Select(attrs={"class": "form-select"}), + "quantite_commander": forms.NumberInput( + attrs={"class": "form-control"} + ), + "prix_achat": forms.NumberInput(attrs={"class": "form-control"}), + "date_commande": forms.DateInput( + attrs={"class": "form-control", "type": "date"} + ), + "date_livraison": forms.DateInput( + attrs={"class": "form-control", "type": "date"} + ), + } + + +class DemanderProduit(forms.ModelForm): + """Formulaire pour l'enregistrement d'une demande de produit.""" + + class Meta: + """Métadonnées du formulaire.""" + + model = Demander + fields = ( + "produit", + "quantite", + "motifs", + "date_de_mise_a_dispo_souhaite", + "a_rendre", + ) + widgets = { + "produit": forms.Select(attrs={"class": "form-select"}), + "quantite": forms.NumberInput(attrs={"class": "form-control"}), + "motifs": forms.Textarea( + attrs={"class": "form-control", "rows": 4} + ), + "date_de_mise_a_dispo_souhaite": forms.DateInput( + attrs={"class": "form-control", "type": "date"} + ), + "a_rendre": forms.CheckboxInput( + attrs={"class": "form-check-input"} + ), + } diff --git a/gestion_produit/migrations/0001_initial.py b/gestion_produit/migrations/0001_initial.py new file mode 100644 index 0000000..70e599a --- /dev/null +++ b/gestion_produit/migrations/0001_initial.py @@ -0,0 +1,78 @@ +# Generated by Django 5.2.7 on 2025-11-02 12:47 + +import datetime +import django.db.models.deletion +from django.db import migrations, models + + +class Migration(migrations.Migration): + + initial = True + + dependencies = [ + ] + + operations = [ + migrations.CreateModel( + name='Categorie', + fields=[ + ('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')), + ('categorie', models.CharField(max_length=255, unique=True)), + ], + ), + migrations.CreateModel( + name='Fournisseur', + fields=[ + ('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')), + ('nom_entreprise', models.CharField(max_length=100, verbose_name="Nom de l'entreprise")), + ('nom_prenom_representant', models.CharField(max_length=255, verbose_name='Nom et prénom du representant')), + ('fonction', models.CharField(max_length=20, verbose_name='Fonction du représentant')), + ('telephone', models.CharField(max_length=25, verbose_name='Téléphone du représentant')), + ('email', models.EmailField(max_length=254, verbose_name='Adresse e-mail')), + ('note', models.IntegerField(default=0)), + ('categorie', models.ManyToManyField(to='gestion_produit.categorie', verbose_name='Catégorie de produit fourni')), + ], + ), + migrations.CreateModel( + name='Produit', + fields=[ + ('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')), + ('libelle', models.CharField(max_length=255, verbose_name='Libellé')), + ('quantite_stock', models.IntegerField(verbose_name='Quantité actuellement en stock')), + ('conditionnement', models.CharField(choices=[('boite', 'Boite'), ('paquet', 'Paquet'), ('piece', 'Pièce'), ('rouleau', 'Rouleau'), ('carton', 'Carton')], max_length=255, verbose_name='Conditionnement du produit')), + ('seuil_pre_rupture', models.IntegerField(verbose_name='Seuil de pré-rupture')), + ('seuil_rupture', models.IntegerField(verbose_name='Seuil de rupture')), + ('image', models.ImageField(blank=True, null=True, upload_to='produit_image/')), + ('categorie', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='gestion_produit.categorie')), + ], + ), + migrations.CreateModel( + name='Demander', + fields=[ + ('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')), + ('quantite', models.IntegerField(default=1, verbose_name='Quantité demandée')), + ('motifs', models.TextField(blank=True, null=True, verbose_name='Motif (Facultatif)')), + ('dateDemande', models.DateField()), + ('a_rendre', models.BooleanField(default=False)), + ('rendu', models.BooleanField(default=False)), + ('date_rendu', models.DateField(blank=True, null=True)), + ('valider_par_chef', models.BooleanField(default=None, null=True)), + ('valider_par_logisticien', models.BooleanField(default=None, null=True)), + ('motif_refus', models.TextField(default=None, null=True)), + ('livrer', models.BooleanField(default=False)), + ('produit', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='gestion_produit.produit')), + ], + ), + migrations.CreateModel( + name='Commander', + fields=[ + ('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')), + ('quantite_commander', models.IntegerField(verbose_name='Quantité à commander')), + ('date_commande', models.DateField(default=datetime.datetime(2025, 11, 2, 12, 47, 28, 185297, tzinfo=datetime.timezone.utc))), + ('date_livraison', models.DateField(default=datetime.datetime(2025, 11, 2, 12, 47, 28, 185309, tzinfo=datetime.timezone.utc))), + ('livrer', models.BooleanField(default=False)), + ('fournisseur', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='gestion_produit.fournisseur')), + ('produit', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='gestion_produit.produit')), + ], + ), + ] diff --git a/gestion_produit/migrations/0002_alter_commander_date_commande_and_more.py b/gestion_produit/migrations/0002_alter_commander_date_commande_and_more.py new file mode 100644 index 0000000..276bf37 --- /dev/null +++ b/gestion_produit/migrations/0002_alter_commander_date_commande_and_more.py @@ -0,0 +1,29 @@ +# Generated by Django 5.2.7 on 2025-11-06 12:10 + +import datetime +from django.db import migrations, models + + +class Migration(migrations.Migration): + + dependencies = [ + ('gestion_produit', '0001_initial'), + ] + + operations = [ + migrations.AlterField( + model_name='commander', + name='date_commande', + field=models.DateField(default=datetime.datetime(2025, 11, 6, 12, 10, 31, 469244, tzinfo=datetime.timezone.utc)), + ), + migrations.AlterField( + model_name='commander', + name='date_livraison', + field=models.DateField(default=datetime.datetime(2025, 11, 6, 12, 10, 31, 469258, tzinfo=datetime.timezone.utc)), + ), + migrations.AlterField( + model_name='demander', + name='rendu', + field=models.BooleanField(default=None), + ), + ] diff --git a/gestion_produit/migrations/0003_alter_commander_date_commande_and_more.py b/gestion_produit/migrations/0003_alter_commander_date_commande_and_more.py new file mode 100644 index 0000000..c4cc61d --- /dev/null +++ b/gestion_produit/migrations/0003_alter_commander_date_commande_and_more.py @@ -0,0 +1,24 @@ +# Generated by Django 5.2.7 on 2025-11-06 12:56 + +import datetime +from django.db import migrations, models + + +class Migration(migrations.Migration): + + dependencies = [ + ('gestion_produit', '0002_alter_commander_date_commande_and_more'), + ] + + operations = [ + migrations.AlterField( + model_name='commander', + name='date_commande', + field=models.DateField(default=datetime.datetime(2025, 11, 6, 12, 56, 11, 53959, tzinfo=datetime.timezone.utc)), + ), + migrations.AlterField( + model_name='commander', + name='date_livraison', + field=models.DateField(default=datetime.datetime(2025, 11, 6, 12, 56, 11, 53973, tzinfo=datetime.timezone.utc)), + ), + ] diff --git a/gestion_produit/migrations/0004_alter_commander_date_commande_and_more.py b/gestion_produit/migrations/0004_alter_commander_date_commande_and_more.py new file mode 100644 index 0000000..e112910 --- /dev/null +++ b/gestion_produit/migrations/0004_alter_commander_date_commande_and_more.py @@ -0,0 +1,24 @@ +# Generated by Django 5.2.7 on 2025-11-06 12:57 + +import datetime +from django.db import migrations, models + + +class Migration(migrations.Migration): + + dependencies = [ + ('gestion_produit', '0003_alter_commander_date_commande_and_more'), + ] + + operations = [ + migrations.AlterField( + model_name='commander', + name='date_commande', + field=models.DateField(default=datetime.datetime(2025, 11, 6, 12, 57, 18, 682229, tzinfo=datetime.timezone.utc)), + ), + migrations.AlterField( + model_name='commander', + name='date_livraison', + field=models.DateField(default=datetime.datetime(2025, 11, 6, 12, 57, 18, 682244, tzinfo=datetime.timezone.utc)), + ), + ] diff --git a/gestion_produit/migrations/0005_alter_commander_date_commande_and_more.py b/gestion_produit/migrations/0005_alter_commander_date_commande_and_more.py new file mode 100644 index 0000000..4e96483 --- /dev/null +++ b/gestion_produit/migrations/0005_alter_commander_date_commande_and_more.py @@ -0,0 +1,24 @@ +# Generated by Django 5.2.7 on 2025-11-06 18:37 + +import datetime +from django.db import migrations, models + + +class Migration(migrations.Migration): + + dependencies = [ + ('gestion_produit', '0004_alter_commander_date_commande_and_more'), + ] + + operations = [ + migrations.AlterField( + model_name='commander', + name='date_commande', + field=models.DateField(default=datetime.datetime(2025, 11, 6, 18, 37, 57, 520334, tzinfo=datetime.timezone.utc)), + ), + migrations.AlterField( + model_name='commander', + name='date_livraison', + field=models.DateField(default=datetime.datetime(2025, 11, 6, 18, 37, 57, 520350, tzinfo=datetime.timezone.utc)), + ), + ] diff --git a/gestion_produit/migrations/0006_alter_commander_date_commande_and_more.py b/gestion_produit/migrations/0006_alter_commander_date_commande_and_more.py new file mode 100644 index 0000000..e231e37 --- /dev/null +++ b/gestion_produit/migrations/0006_alter_commander_date_commande_and_more.py @@ -0,0 +1,24 @@ +# Generated by Django 5.2.7 on 2025-11-07 09:25 + +import datetime +from django.db import migrations, models + + +class Migration(migrations.Migration): + + dependencies = [ + ('gestion_produit', '0005_alter_commander_date_commande_and_more'), + ] + + operations = [ + migrations.AlterField( + model_name='commander', + name='date_commande', + field=models.DateField(default=datetime.datetime(2025, 11, 7, 9, 25, 25, 195406, tzinfo=datetime.timezone.utc)), + ), + migrations.AlterField( + model_name='commander', + name='date_livraison', + field=models.DateField(default=datetime.datetime(2025, 11, 7, 9, 25, 25, 195419, tzinfo=datetime.timezone.utc)), + ), + ] diff --git a/gestion_produit/migrations/0007_alter_commander_date_commande_and_more.py b/gestion_produit/migrations/0007_alter_commander_date_commande_and_more.py new file mode 100644 index 0000000..db142e5 --- /dev/null +++ b/gestion_produit/migrations/0007_alter_commander_date_commande_and_more.py @@ -0,0 +1,24 @@ +# Generated by Django 5.2.7 on 2025-11-07 09:25 + +import datetime +from django.db import migrations, models + + +class Migration(migrations.Migration): + + dependencies = [ + ('gestion_produit', '0006_alter_commander_date_commande_and_more'), + ] + + operations = [ + migrations.AlterField( + model_name='commander', + name='date_commande', + field=models.DateField(default=datetime.datetime(2025, 11, 7, 9, 25, 53, 810991, tzinfo=datetime.timezone.utc)), + ), + migrations.AlterField( + model_name='commander', + name='date_livraison', + field=models.DateField(default=datetime.datetime(2025, 11, 7, 9, 25, 53, 811005, tzinfo=datetime.timezone.utc)), + ), + ] diff --git a/gestion_produit/migrations/0008_alter_commander_date_commande_and_more.py b/gestion_produit/migrations/0008_alter_commander_date_commande_and_more.py new file mode 100644 index 0000000..87ba173 --- /dev/null +++ b/gestion_produit/migrations/0008_alter_commander_date_commande_and_more.py @@ -0,0 +1,24 @@ +# Generated by Django 5.2.7 on 2025-11-07 09:29 + +import datetime +from django.db import migrations, models + + +class Migration(migrations.Migration): + + dependencies = [ + ('gestion_produit', '0007_alter_commander_date_commande_and_more'), + ] + + operations = [ + migrations.AlterField( + model_name='commander', + name='date_commande', + field=models.DateField(default=datetime.datetime(2025, 11, 7, 9, 29, 48, 732636, tzinfo=datetime.timezone.utc)), + ), + migrations.AlterField( + model_name='commander', + name='date_livraison', + field=models.DateField(default=datetime.datetime(2025, 11, 7, 9, 29, 48, 732652, tzinfo=datetime.timezone.utc)), + ), + ] diff --git a/gestion_produit/migrations/0009_alter_commander_date_commande_and_more.py b/gestion_produit/migrations/0009_alter_commander_date_commande_and_more.py new file mode 100644 index 0000000..a853a97 --- /dev/null +++ b/gestion_produit/migrations/0009_alter_commander_date_commande_and_more.py @@ -0,0 +1,24 @@ +# Generated by Django 5.2.7 on 2025-11-07 17:11 + +import datetime +from django.db import migrations, models + + +class Migration(migrations.Migration): + + dependencies = [ + ('gestion_produit', '0008_alter_commander_date_commande_and_more'), + ] + + operations = [ + migrations.AlterField( + model_name='commander', + name='date_commande', + field=models.DateField(default=datetime.datetime(2025, 11, 7, 17, 11, 25, 877850, tzinfo=datetime.timezone.utc)), + ), + migrations.AlterField( + model_name='commander', + name='date_livraison', + field=models.DateField(default=datetime.datetime(2025, 11, 7, 17, 11, 25, 877865, tzinfo=datetime.timezone.utc)), + ), + ] diff --git a/gestion_produit/migrations/0010_alter_commander_date_commande_and_more.py b/gestion_produit/migrations/0010_alter_commander_date_commande_and_more.py new file mode 100644 index 0000000..d5f9e3d --- /dev/null +++ b/gestion_produit/migrations/0010_alter_commander_date_commande_and_more.py @@ -0,0 +1,24 @@ +# Generated by Django 5.2.7 on 2025-11-10 15:17 + +import datetime +from django.db import migrations, models + + +class Migration(migrations.Migration): + + dependencies = [ + ('gestion_produit', '0009_alter_commander_date_commande_and_more'), + ] + + operations = [ + migrations.AlterField( + model_name='commander', + name='date_commande', + field=models.DateField(default=datetime.datetime(2025, 11, 10, 15, 17, 2, 22479, tzinfo=datetime.timezone.utc)), + ), + migrations.AlterField( + model_name='commander', + name='date_livraison', + field=models.DateField(default=datetime.datetime(2025, 11, 10, 15, 17, 2, 22493, tzinfo=datetime.timezone.utc)), + ), + ] diff --git a/gestion_produit/migrations/0011_alter_commander_date_commande_and_more.py b/gestion_produit/migrations/0011_alter_commander_date_commande_and_more.py new file mode 100644 index 0000000..a04c3af --- /dev/null +++ b/gestion_produit/migrations/0011_alter_commander_date_commande_and_more.py @@ -0,0 +1,24 @@ +# Generated by Django 5.2.7 on 2025-11-11 07:12 + +import datetime +from django.db import migrations, models + + +class Migration(migrations.Migration): + + dependencies = [ + ('gestion_produit', '0010_alter_commander_date_commande_and_more'), + ] + + operations = [ + migrations.AlterField( + model_name='commander', + name='date_commande', + field=models.DateField(default=datetime.datetime(2025, 11, 11, 7, 12, 38, 131014, tzinfo=datetime.timezone.utc)), + ), + migrations.AlterField( + model_name='commander', + name='date_livraison', + field=models.DateField(default=datetime.datetime(2025, 11, 11, 7, 12, 38, 131028, tzinfo=datetime.timezone.utc)), + ), + ] diff --git a/gestion_produit/migrations/0012_alter_commander_date_commande_and_more.py b/gestion_produit/migrations/0012_alter_commander_date_commande_and_more.py new file mode 100644 index 0000000..e74f251 --- /dev/null +++ b/gestion_produit/migrations/0012_alter_commander_date_commande_and_more.py @@ -0,0 +1,29 @@ +# Generated by Django 5.2.7 on 2025-11-11 20:05 + +import datetime +from django.db import migrations, models + + +class Migration(migrations.Migration): + + dependencies = [ + ('gestion_produit', '0011_alter_commander_date_commande_and_more'), + ] + + operations = [ + migrations.AlterField( + model_name='commander', + name='date_commande', + field=models.DateField(default=datetime.datetime(2025, 11, 11, 20, 5, 28, 333864, tzinfo=datetime.timezone.utc)), + ), + migrations.AlterField( + model_name='commander', + name='date_livraison', + field=models.DateField(default=datetime.datetime(2025, 11, 11, 20, 5, 28, 333879, tzinfo=datetime.timezone.utc)), + ), + migrations.AlterField( + model_name='demander', + name='rendu', + field=models.BooleanField(blank=True, default=None, null=True), + ), + ] diff --git a/gestion_produit/migrations/0013_alter_commander_date_commande_and_more.py b/gestion_produit/migrations/0013_alter_commander_date_commande_and_more.py new file mode 100644 index 0000000..fcb2a59 --- /dev/null +++ b/gestion_produit/migrations/0013_alter_commander_date_commande_and_more.py @@ -0,0 +1,24 @@ +# Generated by Django 5.2.7 on 2025-11-12 12:03 + +import datetime +from django.db import migrations, models + + +class Migration(migrations.Migration): + + dependencies = [ + ('gestion_produit', '0012_alter_commander_date_commande_and_more'), + ] + + operations = [ + migrations.AlterField( + model_name='commander', + name='date_commande', + field=models.DateField(default=datetime.datetime(2025, 11, 12, 12, 3, 36, 708709, tzinfo=datetime.timezone.utc)), + ), + migrations.AlterField( + model_name='commander', + name='date_livraison', + field=models.DateField(default=datetime.datetime(2025, 11, 12, 12, 3, 36, 708742, tzinfo=datetime.timezone.utc)), + ), + ] diff --git a/gestion_produit/migrations/0014_demander_user_alter_commander_date_commande_and_more.py b/gestion_produit/migrations/0014_demander_user_alter_commander_date_commande_and_more.py new file mode 100644 index 0000000..1ef61c7 --- /dev/null +++ b/gestion_produit/migrations/0014_demander_user_alter_commander_date_commande_and_more.py @@ -0,0 +1,36 @@ +# Generated by Django 5.2.7 on 2025-11-18 09:59 + +import datetime +import django.db.models.deletion +from django.db import migrations, models + + +class Migration(migrations.Migration): + + dependencies = [ + ('authentification', '0001_initial'), + ('gestion_produit', '0013_alter_commander_date_commande_and_more'), + ] + + operations = [ + migrations.AddField( + model_name='demander', + name='user', + field=models.ForeignKey(blank=True, null=True, on_delete=django.db.models.deletion.SET_NULL, to='authentification.profile'), + ), + migrations.AlterField( + model_name='commander', + name='date_commande', + field=models.DateField(default=datetime.datetime(2025, 11, 18, 9, 58, 56, 150274, tzinfo=datetime.timezone.utc)), + ), + migrations.AlterField( + model_name='commander', + name='date_livraison', + field=models.DateField(default=datetime.datetime(2025, 11, 18, 9, 58, 56, 150300, tzinfo=datetime.timezone.utc)), + ), + migrations.AlterField( + model_name='demander', + name='motifs', + field=models.TextField(verbose_name='Motif'), + ), + ] diff --git a/gestion_produit/migrations/0015_remove_produit_seuil_rupture_and_more.py b/gestion_produit/migrations/0015_remove_produit_seuil_rupture_and_more.py new file mode 100644 index 0000000..eddb9af --- /dev/null +++ b/gestion_produit/migrations/0015_remove_produit_seuil_rupture_and_more.py @@ -0,0 +1,33 @@ +# Generated by Django 5.2.7 on 2025-11-21 11:49 + +import datetime +from django.db import migrations, models + + +class Migration(migrations.Migration): + + dependencies = [ + ('gestion_produit', '0014_demander_user_alter_commander_date_commande_and_more'), + ] + + operations = [ + migrations.RemoveField( + model_name='produit', + name='seuil_rupture', + ), + migrations.AlterField( + model_name='commander', + name='date_commande', + field=models.DateField(default=datetime.datetime(2025, 11, 21, 11, 49, 7, 470405, tzinfo=datetime.timezone.utc)), + ), + migrations.AlterField( + model_name='commander', + name='date_livraison', + field=models.DateField(default=datetime.datetime(2025, 11, 21, 11, 49, 7, 470419, tzinfo=datetime.timezone.utc)), + ), + migrations.AlterField( + model_name='demander', + name='dateDemande', + field=models.DateField(verbose_name='Date de la demande'), + ), + ] diff --git a/gestion_produit/migrations/0016_alter_commander_date_commande_and_more.py b/gestion_produit/migrations/0016_alter_commander_date_commande_and_more.py new file mode 100644 index 0000000..dd42e3c --- /dev/null +++ b/gestion_produit/migrations/0016_alter_commander_date_commande_and_more.py @@ -0,0 +1,24 @@ +# Generated by Django 5.2.7 on 2025-11-23 10:56 + +import datetime +from django.db import migrations, models + + +class Migration(migrations.Migration): + + dependencies = [ + ('gestion_produit', '0015_remove_produit_seuil_rupture_and_more'), + ] + + operations = [ + migrations.AlterField( + model_name='commander', + name='date_commande', + field=models.DateField(default=datetime.datetime(2025, 11, 23, 10, 56, 56, 731087, tzinfo=datetime.timezone.utc)), + ), + migrations.AlterField( + model_name='commander', + name='date_livraison', + field=models.DateField(default=datetime.datetime(2025, 11, 23, 10, 56, 56, 731101, tzinfo=datetime.timezone.utc)), + ), + ] diff --git a/gestion_produit/migrations/0017_alter_commander_date_commande_and_more.py b/gestion_produit/migrations/0017_alter_commander_date_commande_and_more.py new file mode 100644 index 0000000..3cc30a2 --- /dev/null +++ b/gestion_produit/migrations/0017_alter_commander_date_commande_and_more.py @@ -0,0 +1,24 @@ +# Generated by Django 5.2.7 on 2025-11-23 13:11 + +import datetime +from django.db import migrations, models + + +class Migration(migrations.Migration): + + dependencies = [ + ('gestion_produit', '0016_alter_commander_date_commande_and_more'), + ] + + operations = [ + migrations.AlterField( + model_name='commander', + name='date_commande', + field=models.DateField(default=datetime.datetime(2025, 11, 23, 13, 11, 5, 285244, tzinfo=datetime.timezone.utc)), + ), + migrations.AlterField( + model_name='commander', + name='date_livraison', + field=models.DateField(default=datetime.datetime(2025, 11, 23, 13, 11, 5, 285259, tzinfo=datetime.timezone.utc)), + ), + ] diff --git a/gestion_produit/migrations/0018_alter_commander_date_commande_and_more.py b/gestion_produit/migrations/0018_alter_commander_date_commande_and_more.py new file mode 100644 index 0000000..867cf58 --- /dev/null +++ b/gestion_produit/migrations/0018_alter_commander_date_commande_and_more.py @@ -0,0 +1,24 @@ +# Generated by Django 5.2.7 on 2025-11-23 13:12 + +import datetime +from django.db import migrations, models + + +class Migration(migrations.Migration): + + dependencies = [ + ('gestion_produit', '0017_alter_commander_date_commande_and_more'), + ] + + operations = [ + migrations.AlterField( + model_name='commander', + name='date_commande', + field=models.DateField(default=datetime.datetime(2025, 11, 23, 13, 12, 3, 530224, tzinfo=datetime.timezone.utc)), + ), + migrations.AlterField( + model_name='commander', + name='date_livraison', + field=models.DateField(default=datetime.datetime(2025, 11, 23, 13, 12, 3, 530238, tzinfo=datetime.timezone.utc)), + ), + ] diff --git a/gestion_produit/migrations/0019_alter_commander_date_commande_and_more.py b/gestion_produit/migrations/0019_alter_commander_date_commande_and_more.py new file mode 100644 index 0000000..62c0ee4 --- /dev/null +++ b/gestion_produit/migrations/0019_alter_commander_date_commande_and_more.py @@ -0,0 +1,24 @@ +# Generated by Django 5.2.7 on 2025-11-23 13:13 + +import datetime +from django.db import migrations, models + + +class Migration(migrations.Migration): + + dependencies = [ + ('gestion_produit', '0018_alter_commander_date_commande_and_more'), + ] + + operations = [ + migrations.AlterField( + model_name='commander', + name='date_commande', + field=models.DateField(default=datetime.datetime(2025, 11, 23, 13, 12, 59, 980820, tzinfo=datetime.timezone.utc)), + ), + migrations.AlterField( + model_name='commander', + name='date_livraison', + field=models.DateField(default=datetime.datetime(2025, 11, 23, 13, 12, 59, 980834, tzinfo=datetime.timezone.utc)), + ), + ] diff --git a/gestion_produit/migrations/0020_alter_commander_date_commande_and_more.py b/gestion_produit/migrations/0020_alter_commander_date_commande_and_more.py new file mode 100644 index 0000000..0085dbc --- /dev/null +++ b/gestion_produit/migrations/0020_alter_commander_date_commande_and_more.py @@ -0,0 +1,24 @@ +# Generated by Django 5.2.7 on 2025-11-23 13:26 + +import datetime +from django.db import migrations, models + + +class Migration(migrations.Migration): + + dependencies = [ + ('gestion_produit', '0019_alter_commander_date_commande_and_more'), + ] + + operations = [ + migrations.AlterField( + model_name='commander', + name='date_commande', + field=models.DateField(default=datetime.datetime(2025, 11, 23, 13, 26, 54, 601389, tzinfo=datetime.timezone.utc)), + ), + migrations.AlterField( + model_name='commander', + name='date_livraison', + field=models.DateField(default=datetime.datetime(2025, 11, 23, 13, 26, 54, 601404, tzinfo=datetime.timezone.utc)), + ), + ] diff --git a/gestion_produit/migrations/0021_commander_prix_achat_alter_commander_date_commande_and_more.py b/gestion_produit/migrations/0021_commander_prix_achat_alter_commander_date_commande_and_more.py new file mode 100644 index 0000000..b3bcbcf --- /dev/null +++ b/gestion_produit/migrations/0021_commander_prix_achat_alter_commander_date_commande_and_more.py @@ -0,0 +1,34 @@ +# Generated by Django 5.2.7 on 2025-11-23 14:16 + +import datetime +from django.db import migrations, models + + +class Migration(migrations.Migration): + + dependencies = [ + ('gestion_produit', '0020_alter_commander_date_commande_and_more'), + ] + + operations = [ + migrations.AddField( + model_name='commander', + name='prix_achat', + field=models.IntegerField(default=0, verbose_name="Prix d'achat unitaire :"), + ), + migrations.AlterField( + model_name='commander', + name='date_commande', + field=models.DateField(default=datetime.datetime(2025, 11, 23, 14, 16, 9, 450472, tzinfo=datetime.timezone.utc)), + ), + migrations.AlterField( + model_name='commander', + name='date_livraison', + field=models.DateField(default=datetime.datetime(2025, 11, 23, 14, 16, 9, 450488, tzinfo=datetime.timezone.utc)), + ), + migrations.AlterField( + model_name='commander', + name='quantite_commander', + field=models.IntegerField(default=0, verbose_name='Quantité à commander'), + ), + ] diff --git a/gestion_produit/migrations/0022_fournisseur_nifp_fournisseur_rccm_and_more.py b/gestion_produit/migrations/0022_fournisseur_nifp_fournisseur_rccm_and_more.py new file mode 100644 index 0000000..8b6e508 --- /dev/null +++ b/gestion_produit/migrations/0022_fournisseur_nifp_fournisseur_rccm_and_more.py @@ -0,0 +1,34 @@ +# Generated by Django 5.2.7 on 2025-11-23 15:07 + +import datetime +from django.db import migrations, models + + +class Migration(migrations.Migration): + + dependencies = [ + ('gestion_produit', '0021_commander_prix_achat_alter_commander_date_commande_and_more'), + ] + + operations = [ + migrations.AddField( + model_name='fournisseur', + name='nifp', + field=models.FileField(blank=True, null=True, upload_to='fournisseur/nifp/', verbose_name='Le NIFp du fournisseur :'), + ), + migrations.AddField( + model_name='fournisseur', + name='rccm', + field=models.FileField(blank=True, null=True, upload_to='fournisseur/rccm/', verbose_name='Le RCCM du fournisseur :'), + ), + migrations.AlterField( + model_name='commander', + name='date_commande', + field=models.DateField(default=datetime.datetime(2025, 11, 23, 15, 7, 4, 171371, tzinfo=datetime.timezone.utc)), + ), + migrations.AlterField( + model_name='commander', + name='date_livraison', + field=models.DateField(default=datetime.datetime(2025, 11, 23, 15, 7, 4, 171386, tzinfo=datetime.timezone.utc)), + ), + ] diff --git a/gestion_produit/migrations/0023_alter_commander_date_commande_and_more.py b/gestion_produit/migrations/0023_alter_commander_date_commande_and_more.py new file mode 100644 index 0000000..962aa05 --- /dev/null +++ b/gestion_produit/migrations/0023_alter_commander_date_commande_and_more.py @@ -0,0 +1,29 @@ +# Generated by Django 5.2.7 on 2025-11-24 09:27 + +import datetime +from django.db import migrations, models + + +class Migration(migrations.Migration): + + dependencies = [ + ('gestion_produit', '0022_fournisseur_nifp_fournisseur_rccm_and_more'), + ] + + operations = [ + migrations.AlterField( + model_name='commander', + name='date_commande', + field=models.DateField(default=datetime.datetime(2025, 11, 24, 9, 27, 40, 858764, tzinfo=datetime.timezone.utc)), + ), + migrations.AlterField( + model_name='commander', + name='date_livraison', + field=models.DateField(default=datetime.datetime(2025, 11, 24, 9, 27, 40, 858784, tzinfo=datetime.timezone.utc)), + ), + migrations.AlterField( + model_name='demander', + name='rendu', + field=models.BooleanField(default=False), + ), + ] diff --git a/gestion_produit/migrations/0024_alter_commander_date_commande_and_more.py b/gestion_produit/migrations/0024_alter_commander_date_commande_and_more.py new file mode 100644 index 0000000..e98f7f9 --- /dev/null +++ b/gestion_produit/migrations/0024_alter_commander_date_commande_and_more.py @@ -0,0 +1,54 @@ +# Generated by Django 5.2.7 on 2025-11-24 11:17 + +import datetime +from django.db import migrations, models + + +class Migration(migrations.Migration): + + dependencies = [ + ('gestion_produit', '0023_alter_commander_date_commande_and_more'), + ] + + operations = [ + migrations.AlterField( + model_name='commander', + name='date_commande', + field=models.DateField(default=datetime.datetime(2025, 11, 24, 11, 17, 14, 847774, tzinfo=datetime.timezone.utc)), + ), + migrations.AlterField( + model_name='commander', + name='date_livraison', + field=models.DateField(default=datetime.datetime(2025, 11, 24, 11, 17, 14, 847789, tzinfo=datetime.timezone.utc)), + ), + migrations.AlterField( + model_name='commander', + name='prix_achat', + field=models.PositiveIntegerField(default=0, verbose_name="Prix d'achat unitaire :"), + ), + migrations.AlterField( + model_name='commander', + name='quantite_commander', + field=models.PositiveIntegerField(default=1, verbose_name='Quantité à commander'), + ), + migrations.AlterField( + model_name='demander', + name='quantite', + field=models.PositiveIntegerField(default=1, verbose_name='Quantité demandée'), + ), + migrations.AlterField( + model_name='fournisseur', + name='note', + field=models.PositiveIntegerField(default=0), + ), + migrations.AlterField( + model_name='produit', + name='quantite_stock', + field=models.PositiveIntegerField(verbose_name='Quantité actuellement en stock'), + ), + migrations.AlterField( + model_name='produit', + name='seuil_pre_rupture', + field=models.PositiveIntegerField(verbose_name='Seuil de pré-rupture'), + ), + ] diff --git a/gestion_produit/migrations/0025_remove_demander_datedemande_and_more.py b/gestion_produit/migrations/0025_remove_demander_datedemande_and_more.py new file mode 100644 index 0000000..40697b2 --- /dev/null +++ b/gestion_produit/migrations/0025_remove_demander_datedemande_and_more.py @@ -0,0 +1,33 @@ +# Generated by Django 5.2.7 on 2025-12-09 11:08 + +import datetime +from django.db import migrations, models + + +class Migration(migrations.Migration): + + dependencies = [ + ('gestion_produit', '0024_alter_commander_date_commande_and_more'), + ] + + operations = [ + migrations.RemoveField( + model_name='demander', + name='dateDemande', + ), + migrations.AddField( + model_name='demander', + name='dateDeMiseADispoSouhaite', + field=models.DateField(default=datetime.datetime(2025, 12, 9, 11, 8, 12, 53828, tzinfo=datetime.timezone.utc), verbose_name='Date de mise à disposition souhaitée'), + ), + migrations.AlterField( + model_name='commander', + name='date_commande', + field=models.DateField(default=datetime.datetime(2025, 12, 9, 11, 8, 12, 54763, tzinfo=datetime.timezone.utc)), + ), + migrations.AlterField( + model_name='commander', + name='date_livraison', + field=models.DateField(default=datetime.datetime(2025, 12, 9, 11, 8, 12, 54774, tzinfo=datetime.timezone.utc)), + ), + ] diff --git a/gestion_produit/migrations/0026_remove_demander_datedemiseadisposouhaite_and_more.py b/gestion_produit/migrations/0026_remove_demander_datedemiseadisposouhaite_and_more.py new file mode 100644 index 0000000..e86af4c --- /dev/null +++ b/gestion_produit/migrations/0026_remove_demander_datedemiseadisposouhaite_and_more.py @@ -0,0 +1,38 @@ +# Generated by Django 5.2.7 on 2025-12-10 15:28 + +import datetime +from django.db import migrations, models + + +class Migration(migrations.Migration): + + dependencies = [ + ('gestion_produit', '0025_remove_demander_datedemande_and_more'), + ] + + operations = [ + migrations.RemoveField( + model_name='demander', + name='dateDeMiseADispoSouhaite', + ), + migrations.AddField( + model_name='demander', + name='date_de_mise_a_dispo_souhaite', + field=models.DateField(default=datetime.datetime(2025, 12, 10, 15, 28, 12, 902256, tzinfo=datetime.timezone.utc), verbose_name='Date de mise à disposition souhaitée'), + ), + migrations.AlterField( + model_name='commander', + name='date_commande', + field=models.DateField(default=datetime.datetime(2025, 12, 10, 15, 28, 12, 903193, tzinfo=datetime.timezone.utc)), + ), + migrations.AlterField( + model_name='commander', + name='date_livraison', + field=models.DateField(default=datetime.datetime(2025, 12, 10, 15, 28, 12, 903203, tzinfo=datetime.timezone.utc)), + ), + migrations.AlterField( + model_name='demander', + name='motif_refus', + field=models.TextField(blank=True, default=''), + ), + ] diff --git a/gestion_produit/migrations/0027_alter_commander_date_commande_and_more.py b/gestion_produit/migrations/0027_alter_commander_date_commande_and_more.py new file mode 100644 index 0000000..3b64f7d --- /dev/null +++ b/gestion_produit/migrations/0027_alter_commander_date_commande_and_more.py @@ -0,0 +1,29 @@ +# Generated by Django 5.2.8 on 2025-12-19 09:39 + +import django.utils.timezone +from django.db import migrations, models + + +class Migration(migrations.Migration): + + dependencies = [ + ('gestion_produit', '0026_remove_demander_datedemiseadisposouhaite_and_more'), + ] + + operations = [ + migrations.AlterField( + model_name='commander', + name='date_commande', + field=models.DateField(default=django.utils.timezone.now), + ), + migrations.AlterField( + model_name='commander', + name='date_livraison', + field=models.DateField(default=django.utils.timezone.now), + ), + migrations.AlterField( + model_name='demander', + name='date_de_mise_a_dispo_souhaite', + field=models.DateField(default=django.utils.timezone.now, verbose_name='Date de mise à disposition souhaitée'), + ), + ] diff --git a/gestion_produit/migrations/__init__.py b/gestion_produit/migrations/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/gestion_produit/migrations/__pycache__/0001_initial.cpython-310.pyc b/gestion_produit/migrations/__pycache__/0001_initial.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..18bb85b08ed1c74ed59506961024a42f08455cd0 GIT binary patch literal 2869 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 literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0002_alter_commander_date_commande_and_more.cpython-310.pyc b/gestion_produit/migrations/__pycache__/0002_alter_commander_date_commande_and_more.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..24fe2f7d4df1b9dd805f762de217b8fc4b6c959b GIT binary patch literal 871 zcmZ`%O^?$s5ViBsrfIre7KsxQ0wF{$P2s`?p#>rK0(;q8E>`GFiz_GYItdbch2vJ@ zZ}69V<z9*tr~>&fRtp8Je_b7u2}BA zp5mpKd!?WIoEppgC^Z!JA$GG|YH`wHrmOjD}V=HknSRkA$pbBMW5*GhLQN z1!(LDiU!5bmzzFgn;}iN={ZOoIQ2Jo2;`54eU@_DYtCdf*JSkp=S8cU)F=I%W}+%e zv_XgAT%rQI*HuvRy(wg^D;cMKW+T9h210`sw8!blMxu)r!p1^SwpJn8i4do4pV*|Kmo)1LbhZ?^yN$Sl5l>--t2i~S@U)#N=aS&# zUgiRsWXpx)u>=*7ZIlz6m1tW`u_)d+AbZj$gjC!ur|K`cR3|o4@URKyEjrYYaph1=4Qj8K4ozeXwDj})`uT%1 z#e@Ef2i8c-D(+jw?VGL1`TfcHPb)jKJL|i}-POJF%HA`3kJegrqe(Yfbh8Q12&mNI-4urS=`j$aL?+|^j- zSlaGQNGZDU6EaYr?-tK(ei>Z&L7`CA@1d$FN=HLV;WL`}rVT6Fd$Uy-YZk`7BXDAZ EpZBm>7XSbN literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0002_commander_livrer_alter_commander_date_commande_and_more.cpython-313.pyc b/gestion_produit/migrations/__pycache__/0002_commander_livrer_alter_commander_date_commande_and_more.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..7b9eb83c3b01996db6d8344fc665f667acdf5a80 GIT binary patch literal 1420 zcmbtU&1(}u6rar|o6VZEaocLEh&3oSR%|T_R;o}xD%4LhEnXIeZFU+*H@k6mQ?Pmv z1U(5}{2%InP;VYRHbF?4iw95jREgd^_-4~}RXm6tlJ_<5&3kWtZ?;<~7zkGJ!}ohH zRfIlCC0>~wp*sh{YlIP2t|Kma>bf$Y;;DI+tD|Tbl@L}BAe^>R6+I44_*pntE}pI_ z<;<28Z;x(`%be||PyM?%d5l>--t2i~G@U)ewS!rLgjsUfcMu1%R?e}GsbEw3*`fP{WTg$>_~(A zPLqWqKRG#hnlO)r%yvbt>euVG=TI&*m#uKh=gNx6I&|4?x?x!b^d;iNv+Go(Bbr%e z)OAF`u|rDYa3=F@$r0Tek)$BWxFjcmu+QsIj3Tsfm3hm)=!;@yKAQ!;$1c1@=nV{8 zQRpN}MTjs6fz(Zxf}AJhVbgYHdeHg_S!O&4UFK2Gm)j0)Q0T#{G8%9>#X_HToHPvu+5DMs4J-KpQ<#msN!f8r3CT^*t)oW>^)5-=Oge7$PJH;Wbo= z9fq7OHA5N@!sQ@!;g7_N%jd1dfbzgvxV>1pI(p}_b%h2GLcd{!+_zl6#sH9qO={t5 zH>^LeTx|6=|P1p-LIt#Nv)@rY|sO+@4*1T7%X(YA(iC%4tq zp!W2}wt;d39sOWiKe)NSw7GX=(;V)Y$J*wxHQF-Ie95MB#*WXSwtgt`8I62OZL_p? zt}{N<9-moXcsKQqzn^-~H}K-dU2B8ZJ9MQ*S2}dH1;6pfE%V7=&pNW3v-THF?b$p( z9`{(z@Dj)(=iIlwnt#e!ism3fzjqT7p`QPkbkt{h({+)b02RJmC^!scTU8XLt0ATM Y5siJ-_9@ycqf|tWfo--+V}-e%;K+$*^H_;(p`9P# z5BL&#BpSC=BmQ6|1lL)1XL%G@^6|aN@%6dKwzFAGaD4kP)q)f9)h9PcfXN}wc7Xr{ zs3DnOnV}WSSj96=$q@k#!FvLMVrB4-X93U?l7w5_Lyi;X;z}1y-f3I6Zd6%Nrd|4f zH^&^4L!9jyf+86Ok};qK&A1B65EyVZD#uEc0s;tO1Y;1mM))NvV~95bCL0RV%@u$4 zPyXKD{DNf@n4{u-7rnYtin8a0YQ1Q=ZY=b=a}N#<4j#(fbgGd{TUB`t7(w2t>r~=5 zS=mOp=$heXzftsdOvrYEZEi;%rXC(6=ue*sNvIoj=ek~5jK-i=d2hOeqlex%S?85< z!GPgPD+6wCC~ovwlk3*j`U@60PNq)Cfh?tqB`Sj6D2%64p7y!%1$+i-t+0uDsa4xB z)ZpT0zP%T|bb~K~xac|dH{?$EqdJWWgvWDRE64k8>0-N9zb^PAY3|~-0WKhYV=I-m z=!Z#-Ej0Rh+N<>B=w295tMmd*af^E8XuY+2s{0k(LK)=PcAKdO8r6p-UQpHxA;#zJ?OCj literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0003_alter_commander_date_commande_and_more.cpython-313.pyc b/gestion_produit/migrations/__pycache__/0003_alter_commander_date_commande_and_more.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..ab4dd2b4fade30fae095dff2ac4fe257d16621d6 GIT binary patch literal 1293 zcmbtU&ui0A9DhmLG|Aent5b(Copp$%u#JhZ$ry-Z$~Hxs>BYb!YhKIKH0fRvVe=vg zp1pYSFVKr;kGr|!T9A%+@!+X=sZ{TNU$(6N01@{{zTeOH`@Z@9Zu_~Mf#7_3ou!(B z&}SheCw&C^D*#?06PeN)VuH(S(yGklRfQ>&XdD%hshmS*%91Nu^6`LQ1Ha<1R9z~i zy8_-V$=qnrIdc`9&CD)HW^O_GOFqLV z%4g*N@|lrY*37e9eY8~I`kkcP-3*ig{U525Ky)8BneRk2xAz`@cHyXC* z0CMb*9E%uqxZyLx^~<`{DWLrzZQ62MuEw<6mW zEZ za{W4m8Ei$wGHBjHAE}q0!Zm6I>UuBn)0!nFi9x&IPN48h@r=87sYVo8F%M^V+ yw4V}&+T!6ZEV0WV!e0jpE&%B%k|gz2B;`M$E8o;nNquQ_@>8w+)OQ3z?BE9<;7JGo literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0004_alter_commander_date_commande_and_more.cpython-310.pyc b/gestion_produit/migrations/__pycache__/0004_alter_commander_date_commande_and_more.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..d43226b92c762f1a80e5395131dd7fcd0bfa9c27 GIT binary patch literal 839 zcma)4yKWOf6rI=FvuisJ6ch+SLt`O%Es+KZML|NO0h)B%j27SVW>&j9&ORcMmbCr? zzJOnvmdYPM6A8hc4T-~}V5B*F@9deGbI)8mnM4G~{PWmEoRF_RxjO_VM>v}~0uZ1D zN&J@;v}6e@dBQ0!wV1h5zM#Kh|H)Pv=^pYS&W9DS7}$YGmb`j^Hi0V z+KC>6mC*&bz5a&6oY$#oY-NOr(D|{GswXSuB89S`D>TMqrOvvv@CWz|^jc#j)zavu zW~jkMuY8Sf{LwYG1##hPEV9p?^jEb86-bX4w$hGw?b1bdt$)4p7g9gQZ9QB;d}>P_ zH)u)`7dA6!>RG4bljFDX9}dU6Mv2kuga7n;zW!MIPDNiy^9Vr_#>Ed2Fv{ptD!%U` vdDSy#LH!VUE`&U-GCPM4ec^qvJz=N+I(p*S^5wOKhtyx>A5XG<`hfogpv&j2 literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0004_alter_commander_date_commande_and_more.cpython-313.pyc b/gestion_produit/migrations/__pycache__/0004_alter_commander_date_commande_and_more.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..6127732e0b4eb3efddfe17ec4b4a668e9133d631 GIT binary patch literal 1298 zcmbtU%}*0S6rbH~x4TOVrJxWKA~qOpngH=5v4)Ts2^v6SI_PPW${J=HkIqZ#9*>ZwgBl6Junu`{wuFym{Zdy-dbJux3A`nWZ80 zO)~LH9)sR8fcFR^tgIp~cXd@+QMtOJacvq+qCCRd1%wl}S~lX#gZ(Dhm5V28N+H>i z@L@p}R-M(j6S2S#gV*|~7O&hf=q)PJyN$Sl5m&LoHLT7lJYgrx=~#KN%UB?i zR5?44#VC(#vmD!vg|Ne&B-U{X8`#7a9s;fLUyhGq`TUy z`+xDwsXUEGd8U>tj0y8WTU>5oWLo_T5(pM)$SOfxdn;r$6CS`em|H0c&lAp*e@=8S>L&~v$>n!-PkLy?>({iXuVCh zT6C*Tw_ETOU$%0uzNZqVb=uaYv)IZE<@7fzd?rqykmMHu3)6k(__bix-RO6%->IWC zWu1@oFH1#Z;b;~X`4wQ{|A9hjpsOj0($kTW{fe&s&_@;hoz>3Hw6ZgY2$;TspZ_mN AAOHXW literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0004_demander_valider_par_chef_and_more.cpython-313.pyc b/gestion_produit/migrations/__pycache__/0004_demander_valider_par_chef_and_more.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..fd86e13e3b70e76cf73811b50ba4a48a8250c167 GIT binary patch literal 1769 zcmb_c&yUka6dv1&V~2#znn3nPX+r>M-AKC&ZKbAKAyKxAvJ-Ql+ZLUiv?5d+L!RM~<6Z63wNDp7ypV?XgndILVT-6jg#r{N}y!do$mA?;DS@ z*))RjQ-ZCBq7XZ&YC$oV%sPJ3B zixov=w3cLZc!}kjNpqR&x2JqLOhG6xXs$^^!5`9Qfzxp#US3~c|A5$DL>Z|Et(NUO zpgDF#k4*w=q!lpAHHVHJc&=-EuJCNz5chyK?$luSltUYK$BTHv?|7c60AU45iEp2=0o@*r53E^o1HE}u~1wBK^RBEwf%UBr>~24jCFkzS}|5Nkxb-55j7$A0-tiF6V4Wgd(jvv7?B&yPb%Jgs^wvz!5x%vm2jScSFiTtM>Wb>Sx6-ZdjW%d=v$3 zD`J5)Y0KjdweZbb)=SK>UVMuz;LwL;$_+BxT0xCt{;amYW-1&U3qi>6qJ+>7=txES zj&!8RdG)(nM`@&=8EDIWZFyL@Fr2?QG!_QN<-T!w-+7Yn8P}et5_Kmo~j|b(AetF|b?djF0?Ag_4>;Tse?pX)4HK5%d?GET(5B}wEdd9c2 zCm!#0;ce{&IWE4~EC1W(!Oi1nF0zVgcb?04Q#Vr8Y|581V>3co5xCQ3+?a; z^!$=rsu2zKN(ipA?9TEixROuqb&l_D%+*|cRglU z9N=hA5fn)&kdy(^52ocVNMFitb0Fw=c>E@EZ_fP)p zZ+_0wG3=w_8#a7>sT5_;a@9J~a@`o{b!Q(g7K=wRD?8Q5rKzf{2FxJq)Kw{QPFAK- zHoRik>2DOh^$FRIvCZws!A%Db96UkLAHVq|rgqew>3U@_^Fgh$zU*R-MmqCkomI+; z0lk%0CD^^;gi@b2nQl$3Kj9`v@x%slAWLZ@iL#(C73LEuPx`EM8@LM8T45*kQmeLM zsKG|hU5_u_)(t)jV#62M8!GX>yIGp7bg?K75t@;c&8hC<%J~_&>d#uirK9rJ}E-y@L=C#>EfeG0NzDD!%Ws v;Cx`lUUM6HHiROpb2EoGL*qlU17WBCBD?3 zzDOlr$z#x40q_=Kgq1bK<*u$Nt14GlHLgvgNt8!eyMS=QR?9~G@nBy7Ub%RprWBGL z3GWwFVbxiUI}r=~Q0Vo*rCwN(XYtA%gWi%NZ?_RwFybm!xQ5j^g(vJ}IUPF>b{Pvq zk}78hwixA+ZI)x+*a$m(lf*hsVFR1k!b9LS{>$+(ET8|=hSMbjXG#hlE@^*>XXH%r zWdARoIhCjJD9_Y#g)w2?i>uv9K^jp1ks1wU^+|&VZj(i#I6pssoj6`ZIjIEoy5qZm zTqmL@Dghg*2b>D?#6x6$b77LdGX!^ZbSY%HJC~&>fncw@DO6B|9_=u{8URYUwCXgy zsGz|_$SEMcQ>P-)m&q!lo-2m?H+XEDJ1h)*_6|rszz_`!gY?}A5f*{K+@?nXrwQ3= zI-aBeZG@02<6-16pZbA3c4>n`a(;!;kjv>5)-9R#ioA^{q`_QWV%1mDtdqg@5eNY~v}HbU-5 zy=x(JtZhsk7*mH6`NPra!`x&$mp{nm-`{8#7Y~YypEh={?QZSm_cr&-8~cy!eOhnR z?H1i`)14MP#b>SD^KYqyX`SY}bQZ46P)>ij%4gyP3Q2wuurS@nj$aFA-OYa2`kgvT zQ`Y&&UyhnE7LR6OiC+N~{y$JC3A&o1C_No1+0W?ecYRdR-&pPJOe;I{1A)>f_zC*9 BNuB@z literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0005_demander_quantite_alter_commander_date_commande_and_more.cpython-313.pyc b/gestion_produit/migrations/__pycache__/0005_demander_quantite_alter_commander_date_commande_and_more.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..caac83074699091cab47806ef1052e36fc96ba49 GIT binary patch literal 1515 zcmbtT&1)M+6rbIdR=aCSmSx8_F``AV zrf)XOxi znZrd~!eu;)OA`Yh|&F@?hlK5couK*(aB^1~>mB=kD8Za^2Q&PhC(Q!$xu zF&g;NZbqFM5?S&+K}qT}Rlr1b{X`Kmv6WDyPUb+c-`*~xx+YC=#KKlo*LVq{vYc!Y zus-)#9EEKEW*Hqr8&{-7lEVp+4uSIgUO>Sv5(1?K3J`engtQosMZiKDMrzupT?)4p zHW`h%dLPod?fZ8Xa-LIe@x4&cHswi3I=2In+V(C~GYeY^m0(b`rQ}f*Qfc%=Q#w(X zrf=&UA+dmW)+C+~oE`QAjS1mvaLN>ZB)`4$j{7jCJa!L0c-VM%{lh!%E{#7GQP&kb za)YSNfau3P>f(F%-G8v|X0O-<{%>Ubr_>TpVSjo3ocxWAmtAqK`x!R@P9ju`#Xo`g z2A!J7zNeiU`jYw8{Zj|oiz91oXswM`E{+%0#?{qPbz@lFc;cPh!h`C;?}eQ0oTXhD zS{KGEweiAwl2#j5Yfo;DHg|@bJ3kyeee)@Q{>Jmelg7cx$L puY#){P5c^&Q$y3Vsfo18&*<_W=CWpf=Zq?s29-;HB5;xo{sORqhOPhr literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0006_alter_commander_date_commande_and_more.cpython-310.pyc b/gestion_produit/migrations/__pycache__/0006_alter_commander_date_commande_and_more.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..3e98a93bf8f689af49b718f125ff7c57a8fa7439 GIT binary patch literal 834 zcma)4%Wl*#6tx{^#>vcdxIh&7%_C!gfA{ zZ{Sb7Wi`K0gy1@*o$^@V$S3zY$Jghc*v@7#!4ZC$X%P_e)hBlc$K(WOyFdT})R4@- znV}WSSQTUeC8q=e;GYO^#Y+A$$T-k5l7u_lLzW41aixnU@3gI3H>xZs)2{rtyJL>Y z3C{KcL6M9C$r#XrW`W{m2n+%>D#uEc0yu;)f-wkuB3y~e7~-vf$(F)&d&8golYj6x zzhKz}=BW74MQ?7DqU?F0S}$5|8VkMd+>@iDqo*=AooeLDR#jdDMv!;vHkG(0E88d+ z-7?(lH;Uek3E54sO&^e5EV&>UwQ48iQKrz3GwwJ@mfGIkrSItmhQ9}-R_pzT@&zP zV&d70|ASsUn|R^K5xA7h#e*kqHPw?B-z+RBCdSCL`{sLZ-hT6bwcUK)La?%*^32c> z`XZHdWsgC30l-^?5muHEm%F;8EUH{x)VMZ^hEWM&?FzyfTdf-D%cuJ^@XEzA4W*nt zlyIf23aiN)+=*D=heB@#F7?8iJWE&c7HEKUCRN^x`+2@mC=UqpVOs6O9HasD?{CmhR-d$Z;KnQxm8q$zY2tVh<)jugn~v`S za-E2ts03`J8E`7h6AzL9&4o$+!ydTf(3Ijb2)6P=MP)_k(H8UT0ic{q>rU)NWew&) z_MZ4olZs3tvvo#2SM(*k9(&Fm76v|B1CsYJI(@<*i8~>}A`p%ndlYalAseydNea;V z38^z4MjrF2AIM{uwkV|J*BA}CoJnEbmB}v1+jvGA%z4N*(S;#zj~E1HNVygGRA_Nj z6IRfo>D&$x5=Jn?HR41OXX|l9LqhlvaCPB9qIK_%y&6&;+7BMt^E7-G1uZ+`f$aqi z2Ib#~sg3V1+h=-VpZ+#%=*q2s?8-!Ilk0G8B4nGx4h5E_ySldPdTlq}bK|zV zxd-3M)?V?&*IdT5&T@^Nhb!Mx)L$*~QkpL^WF=Oh1X w($SbbnuR%j9aQ+&K;cyo9ZgY`u8x$#XLRG6KA`Attaf31uQ2`{fszpX1h0)oQ~&?~ literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0006_demander_motif_refus_alter_commander_date_commande_and_more.cpython-313.pyc b/gestion_produit/migrations/__pycache__/0006_demander_motif_refus_alter_commander_date_commande_and_more.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..133fb2aab780f494483f5c95a6686fab1778250a GIT binary patch literal 1498 zcmbtU&1>976dy^uT1oy|uN~X@th3D_!X+`GDRt`HpB&a?CNuKp=QcV3&c=Lr;5i*p!|MeY0z!wiH^LVfEhc&3kX=H}l@? zaB9jyFkbxj`=?J0gnm&*KFSARcoo2p2qUarM_g(By0)QneZ%0!GFn1)gpDHzmpr{; z<;jIU59_MIOD)YU4-~xN>e6Ym7WV~9;#8XLB%o2+RK9%79f0Atn%dn%T*HX#SmOrP z&uYBnl^c_JaG@0!U{YyRi@6+uuZ&GxS<|t#W)Hsr(LgU#r3)j}Pf8jItT72gJAD^=ZpT>vyOsniJNc+RQ zT7wGEhx*O5XsW75Iy?z7Cgg?H)z$MPplv@6C?~fwKNd_-;zt6^X3{=z1U^jWCV^nm zPB@iTo+&5ViC`h&G|bW)Td-9nprM~dLYCqzid+MFNA(Md{WgU;CCeeBQ6TMnT`s5o zvJX?V2ddWxstki;O1uSv?cA}Dt4UMbWpS9e8dpsvr$^ZlyTg5!CNX;kQ4f$?l@=Lo zONev`5D&750-hx5ypf^;)(jyb_1iPKi2z9=Syw^qmfW8l|BdYJ=!;seN)>v^m+5%=DvgMxt?`&&pO&)JlUT; z(XTD_YW2NZ{inAd2Ho2GFDoV6Ify#GXC3b^*88)|Mbx{!mG!-q^+#Ke&pqZ(&OPC~ zczgGgo4aA$3wOHVPA~kb3%`}GyR~orajlcDv({p@W`4K9Pv^&U%lu8i(hffJ<5qGe zxHam9Q3s4KLltTq@2Ws+ecWLm@D(uOe-Nc_fY>)QO&gj>tNx5mzcLpz^9QF_J=LwA K`W1mOTHp^K4TJ;$ literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0007_alter_commander_date_commande_and_more.cpython-310.pyc b/gestion_produit/migrations/__pycache__/0007_alter_commander_date_commande_and_more.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..b17079fa00d20256c63e0eadc83f4df1310600df GIT binary patch literal 839 zcma)4%Wl*#6!jySaWa!m*&u-s2#HOEG?`6dgHVwW-9R_pWn+c8p5Q2nr+HMOTiDKr z@D2Qlx2$HxzETC(DeaWU0!u!**E#k*_t++iLW1M**GLOa$TyeV9v&u#INLb_5TGSV z-ItZLVkxV5$|*S_z`^@Wz*DU7KJnB8dO~7eh}b1FCG7?%(Y( z!{iWWdxoG$N`a&dXiihEyut?tT#bsc5`_Q{d>FwP1OyP`N>GF_*$9|!C`6lU{@y?N zv%mQ{ODC|8itpIq-L+DbJzip$*k;DBbTPCvKlagtW!6s#5Gx& zM%mzoVWZzDdOId$JHa+xK(>K{dkzi|^mjQWF}0)aT-Pgu(HPV!>&q_YXrwbw)>);j zH=w`Lssy_?R4DaXlj+vf`VtR0j;B`0fh?sBCCY-nR2WaCJngg69pExhYlWTEORd_5 zp#~eiay`CrM>qH^hz(w2lS6KWE7fUKARL~XT3OzAOBoB68XuY+2s`~((IdweFRmc9z5;IHLFJx-xLapi7_&1-+b@Q>-XN9_jbF5f`wp>d@L|S zL+G{`-FX0S5Jp&8L|pFbqOzcJbwT6WFd9Tiw0HFz=Z#AusRoReY-1p7krsG`}mZLe^r( zlN6x!5wgm77F}N=B#dB?Ys85n&Q{`xhJgou(UG~RbToB9f3eiD zka?>^X!Gjk+SbTcb^9USUVgmodM!8J zapRV|z5~zL#!l(^*IdT5j&qHigsad~(qAs{OKAa>EWZF)nC=tDuLtAqO47BYQ~PDg zd*1gSm5#>D{w&P$%b>zv2MRBO=xBR literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0007_demander_livrer_alter_commander_date_commande_and_more.cpython-313.pyc b/gestion_produit/migrations/__pycache__/0007_demander_livrer_alter_commander_date_commande_and_more.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..96e086263203385a89413315efefeaf49c18b401 GIT binary patch literal 1482 zcmbtU&2Q646d%WlW1F@~-O?5i+7du&REbsuciYI>TS=@U>_ zE}m~F)xto+Yt@`Eo2vliojRE+Ny$!t14t$>3*gmLdOPVPiK26svvt$Z6>uc4LK&>gU9eV zp1>tshN!vBo1)tO6lEGuuIfL)$J!O2sh{Jsr1A+o%}b5F)fr)2O?x#c0)6OSsX-&z zJJRBz+h(yiv%I`~lDM?#1TN*I8OF>boO{ec{bK}m{b z5bV_@1Hlnm{DcKwC?=9zd9=f#Fkm0S{SS<4S?DA=l@MVP;Oe%03V4i=hi%7~Ou#A; z;xQh@J_~3NO1Dc}6z(FZGa7OE284drb=M_jo|op>xiIvp6C_*0JS(qhgpCVuMI)$7 zRxyL$tV{VM45(1sab1{Ui>B{qFCkG3Z>dh4IOgnbJEjpKd>@=Lgf9{=&;M#~MwCbP z&Fh=Bi}N?m+ZSl`AP!r0%tPA`8w}d{uuW}z>5BbLZ|&@*+R)`wS(itB`oRVtYyH7B zAd?6=Mo|~UOSG*afrvyOJHqpxYlI{vF3ySVo6%{MD=_`8*Nd<$=G-MYQy1wHR^$9vrK zo_64~_^e|+|8A{AyQwu>wzL-;d?Edj)dD{ZSQzeoCuoGn+`GvfB;6lfh3wEMzA6Lt uwb69_#uvea|2-7_0%BWL6lJI(rTiaS_@K=w+Fxd`e56x8@)3cN6!;7#=Y13a literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0008_alter_commander_date_commande_and_more.cpython-310.pyc b/gestion_produit/migrations/__pycache__/0008_alter_commander_date_commande_and_more.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..c21c17db44357d9d29927e4a60101a264d4cb94b GIT binary patch literal 839 zcma)4yN=W_6!j}JNoHneX($knh9*L6rh@{ZMM7)?+iaJ{3UfWdkrU76u@c)tJ0HS7 z@Ff-<)ku87N(ipA?9TEiu;i0_onzl~k8NkOnBbUxp6QSi^3^9dhrr|zXM2DE1gIgI z|1v`>ma&RwoRT8~9K=TgLa|bO;F$n=LXu#Md&qIZTwLj*$vbW9){QC)%Ct-W@8+0e za)`4%Lr^56Kr#ljpcz-941fVwqjIdmG6Vquj9?5QL=fXjRK_sbgfQJum~F23d;jFm z|K=Ago4`IQzU87fS4vU#yilzdE!T~OUU%-%VzGE4bJM9tE^SriHDCmJr>;|pYqGM9 za?v%z&3>ck?U<151l#lh*+w4jc~~ImFOMfAp>EWj>w0A|8iQKpz3CE;MtbvPoma|< z0fUuR2Hf6I!RWIl*R8GfH$3DxnYvI8WGP)NQ5N(@VLX-cw9kz{z-OS=3OlKnTD1*B z4K9A+dwk`OZtz(U7rn$Lhunp}RHsov=<(dv%JIHiy4bGOuUq~^n)|qIfD1_9*-E7? znqpF83yr3p_9{I&dY%5^aJqXaDSG|%KfOL!zi<3Y^>(&*5kkVa_#pyD8GT5__gxfT u49p~G?jX-aQ08@E58&<4_|WV?*y+EF9(Z>6?9#&L)E650LTsPj=05=sR_F}? literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0008_alter_commander_date_commande_and_more.cpython-313.pyc b/gestion_produit/migrations/__pycache__/0008_alter_commander_date_commande_and_more.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..e108a8794df0451bbb72a06bc94d4a236443ffb9 GIT binary patch literal 1293 zcmbtUL2J}N6rLoz*(BX})NcI`?*& z3uKb36??W6m62`MQr^@EJA9MHI#zHF8`#7acn$q>d_FfLkfcqb4(oo($Y4gC1StP2Hlan`y<3*H{deCY) zz6;28B6_3}u#r~4sW6W`MBz6VCi(aJAjY04#fTJ>AlRp?eW;=cJz8geBLI|hX~T)V zsG`9z$N?a})1o4i$ZUgA&lUX%xyPPyhlPR9z5>ZRn4f-Oki?x3VG+p5jXerDPsnQQ zc#;CN0YVy#hmps8>Id@JrELmz`E^D^E(cRsw`9fhG8)fFgE)WO0-*Oq#I?i?RBwU5QlKygmUrGz8Wchi(!gQZFelr+%SCXzJojNE} z-t&R~m~=E|4rXDNUj`NaI#754#J;8|N>@ip@iV&eT_05R*H))Ewp|?ifj~(Jege=+ BM<@UQ literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0009_alter_commander_date_commande_and_more.cpython-310.pyc b/gestion_produit/migrations/__pycache__/0009_alter_commander_date_commande_and_more.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..d3e458bfb3043848497dbbdae1d5312db413113a GIT binary patch literal 834 zcma)4%Z}496!j}@lD5-fg9HLrEQpYrED`784vVpB(6z6Y|X`w}-&w2xq%M00PvI%zv4o z70Xz~Gfv4d0S@8|0ijqaKJ!cfJtax7!#(6AVJ@z8(d3=Bb?Ziz1!dZm|95-LF*(B7 zo+BudQ6L!uTF{IuQ3k+(t5G>tVHtve07fuI3?agmsEi@rhA`Pum~OB6vw!jr{^l1f zo4_0uAG+xMwNjKlFI4MA%S~gU*PVO1TrQu<+;pmuD_d204H!Y*shd>dnyhT2Ty(>5 zv)?FsHzs5^!8UzBc6U77L(uotj3m^Jx(i*eEk%2Ez!qG$To2>InIWb_c*2;i8 z7>XNx-sHNqwN9|eNiubz9LQ3-SfV26jly^;r;h>PA}e?#sKCLql`YL;`=@dF9&84G~R3% mL7CTuUBHK-@uAs)u-AVTJ@V}E#g&Dxs6S}r4`PS(F8>KevgL08 literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0009_alter_commander_date_commande_and_more.cpython-313.pyc b/gestion_produit/migrations/__pycache__/0009_alter_commander_date_commande_and_more.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..9fb29a177aa09ea3f74b8e23249595b3715cb426 GIT binary patch literal 1288 zcmbtU&ubGw6rSBpHoM!TO=7FHP^_^+L!d2!&`2$arAk{xGS$<&a-4v`I z1i`Zx{|CKz_Sj>OO)n{P@!%=9Nc8TTv}?42h#hv{eDBTMZ{Dw@pUGGV*6q1bW@!k0 zkxIOhr=Y(E;2pvUD;tQ*UENUDRj#gUT$@3YsDQ9Gg>b@FD@OeBaK8z>a`8l6DJHuT zJ}j!jYOp$YA{O|e&>MkEy|60J;*~!I{S`&tZX>Q>#8s?t4XXR{S3INt z7teyq(|C+$>e*sWm=EG=cTbYWc!0WMH?yxZMSrJG+!03z$gACjW5f*`P+?GcHrwQ3>wJK}-u1$74H z-)T`B-`lj$^uiwgHf-oh`5(J7-+az>xOO09o5PPF-k_e2%nhZdspI;q&7OtK3ms$n z$e2F9R5;Gf9OoxH`NC1Y@P4UNT0SZ*f7;r=vA=UrIM_a{Y#lza4{4)AciVKgL-*S7 zlwP#+FTbV|rgfI<>Up>_BYFMxIxoZt6q9@!urS@Hj$aSv-R(iw2Aw)dQ`Y&!|C)3( tmQQA3gC%6s4~tCHoo8ebaM_{?_VbXWQA??+BCu!4HW}M9csH literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0010_alter_commander_date_commande_and_more.cpython-310.pyc b/gestion_produit/migrations/__pycache__/0010_alter_commander_date_commande_and_more.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..ff786ef0c95ea8ded0fc0583765d330ab8a052ad GIT binary patch literal 839 zcma)4yN=W_6t$hlB$=6=T?z_>prMJ7CZSvjp+!P$1KVtYl*S5kJ;9L^&*rfb+d?}Z z!q?DSqM}N}2dsqPI?L`Xj{-|Rxz{=NJ@?ppK92~FZ}g4~974X@}3wZ>=yVx9M@iybu5n#b$B z62=|TTT7w9?2Q$aJa2N@>RNumLr&tE3HV6n+(aB@L9YbHGtSTYT-gI`24W+ylX@jZ z+gJ@IdTx7sX^(F3Sr8Mxz$VAs1h!NsQ9)qwLf67LeYY}^-iTkf{E0LVaN7u%ki65C zNLn;SB}x|(O+D*Ha(etK`NQF4_fV2FeUkpC*UQcO#=cbam9+N}0>T{khwCxQ=p*WW x-$lXY$c(+_9`Z~GWnLG032(>7$7V;uPXAT((6WQ4R~9~_wvcZNv3+{i`3Zlo=p_IE literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0010_alter_commander_date_commande_and_more.cpython-313.pyc b/gestion_produit/migrations/__pycache__/0010_alter_commander_date_commande_and_more.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..300b4b706a6637ce3a4dca958321f4f36c6d1da7 GIT binary patch literal 1298 zcmbtU&ubGw6rSBpHoM!VNz-bJP^_V%A<)KxV5JnqQl+gT8GjsH7`E9-7~Slqv%5m; zMG!oD@qf^ZXOBJhX4^~3fOznfi$tP#-=y7ED~Q-(_s#d-y#3yL^Ip=+W-SEkt5RTw zhR_$OBrAOgdP@M_AdIlGg1Fq(6=hlF>axbQNi>d%2y5pMPT6YJNIpK^uL7@JJk?N2 z>5hbVORBJ%tihd#1%4>>X5dmUtjV)v6%IjfL6OmI#1)LViWRP5bw=SSJ6#=2oR4>z z3uKb1=8tU&Dk9sgCcKFecK9ZZb)3NlHnD{Vz-#oE<3m_I`=<>L&KWp6r{JME?JxP{ zPL)so|MHnp`5+$V*+!u>BFsCg1#tmO=%=K0boriqNA?=GOy28JE_b z*o#UUOoW^Q;yX<$Qhk}OGwQiws2{;&&$z?Fz-OO;Wqhx$9(Ds^4O&<3dQ*~Mnf*AQ&=}-*-J7SPf3Hh2zB>$VaVtagQN^8 zHv^vvEsko!3R*Oo;4_4T5lnN9I8nseS{%`k5IzQ6J$R95-Mnr;2q_Qk+xP568a|DJ zmL2iH_JRh3My$uw#7e+-g=~2E9>gou)seZPbTxHU zf3e!NkU7#eCiaYp{juWy@Z^4Byj>{n6^d`KwafE+<@pcyw`RBa_Uty_!S{C_KHhP? zwj1xdaogS4g{Qo^TX_C0lQON7To+Eml^rPPFPHgLQa~xq&jS{w`^51Z!L+;9?^?f8 z2W858KJdRN9gX>eSyOJV1R# zNB9C(-XSEU`GrcTT&J{C9t#}#M>A-cXoqZurxG z^7sDc7c3jY3>EL&=*^8%lszkC>qLunW1v@^eYRK}EJUt5*@&g7s=Nk_An)XDDsW9y zrja(fW!UL&6tx`@vK?caE+E^9gQp1U^A#ltwLy2G>XpH01ag)4x=TFt(D^3nypom= z=&zL2VE2aNTAeq!YE7-aV3Ct#VnZ>Ig|M+eMbK-B@kEHTKG&{*%RsIrHc>B?Y#W9e zZ2ZEt_sW%S@J0|Dy~O^8+=lL`PN9O(;f1NC_4;mUW3!gOe()#KJi=`QTtfQJR5ESR z51ndLDD?BJm+9&8>+}zE)7>3O(dL8yw0XXM-?&TaoNON=goJtgiu;T*`h@ZyyC}RI tn2Fy!K%R}D%A#L1J9c<@ZQ*n34hq~sY@gouegc>&=|TVi literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0011_alter_commander_date_commande_and_more.cpython-313.pyc b/gestion_produit/migrations/__pycache__/0011_alter_commander_date_commande_and_more.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..29721434ae785a9d2a42eaaccec760534cb72b84 GIT binary patch literal 1288 zcmbtU&1(}u6rb5mHoM!TO=GJ?DAriT5a@>>SSbauRB5Y7wt89^w%JJ--R!2bn}XGY zAb9rT|DYGo9($4=n~K>4a{LHJ*WO9p3I5j z8T`L^rWKyHhIpo$Ees3ePF(GF3etf34^?R>t551Ya2qTV#hIDe8RB>m<)j?cYL4#$ za-E1CsRV4K7H}$zBM*`J&4o$+_5j?`mfdMz0>R$@z^H(Q7Hu)V5&%lMwBj_psG!0e z$lep*sZo*W$z+95&lQ6`UXN{ZhlPR9J^;xZ7@a|(lb$;v!Xyxm+wdshG$9)e$CDJG z4G~gdJd8Z%Q$LW$F0E5Y$uBb+aygU2ydjfalDF}MG#HDJZBG}vyggzNlrH5~;8USC zqOvf9I*sRcl#noj87>niia1+uL^LFXj{;X09wh2FuiN)S%0v71J$sRckD{P%M?A2- zpvs{98x3k(w^r?Ay|DYg4I8>L`;T3jsz2r$T-y_}&EZ=RFHlEA#tQDJ%82%CwPPaV zR7)S<)5rJEbyndjpK3Q0Z=SQzd@$FBxc?s~6ly-ppZDeHXT xe?dCx^9QrAz%POd{~9Pf2cn~5jJq1b*^lV*H*FYeFU?kVvYDOyjzH-V`~(Tmejt$++LP$` z4g3v$#q}N$9Td4mk*!2@082X(M%6n_i(osCs6< zU0xG(_Hfr95d?`TkeC6@Xv~F^yTE{pUfvg8?tud?{(8^{4}3iF^8kXS2ZJSr;qr_> z`YV6@5B>x;kUxNHu!(zX$!(;J$3xh}TDFb<>Z}GVXp)KAmXjy>oMA?PP~@sl$ZCKBthOz<7H%TQ`!`$?QqyZrWjWVq z^+C+jRy83DXHwJ^v)6;CR)iP!0ToUZ zG5&K@q4O~}nvKMFdKOQ0DGYC$nHfIQT8Xq=(*nH^zsKb>scvJC4!%S5Mi(NgQ9~6e zok{G$Nh_km{g=^|hC~+=7h!82{%32Zi+7bBd29oz?;&`Eap$MwGRo*(>ioEBjq%L; u*4+u+>K5KGKICbc=_wp_f^;Hugo{en)*Z|C9PP02Rsb^Z%|(g1h> literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0012_alter_commander_date_commande_and_more.cpython-313.pyc b/gestion_produit/migrations/__pycache__/0012_alter_commander_date_commande_and_more.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..9098bdd6da70af86b40158bb3c86c78195988076 GIT binary patch literal 1451 zcmb_c&ui2`6rOB0*(7$`ZCcw!6m_Z4WkK75Xr%~hQE63Vr+Nwu>1Mi&W|QqCDOf!S zf@d${zfk`JkHwS6ZVzsmiw948tE}FAlWkgmfCxIfdGo!Qm+!rqZzla>(L&ISH)HI* ziqL22WKBB&{hI(@BaE=JjJWJ`%gR!Y=ay8io7L0rLz=di+6oV%d#yrb2Jvf!g$ z)&i9j>ZPNx3{{Y0)-&F05PEn=!#ey5*uW;XAZq-F=>u4w_X;#yn>7K>L2PE z{-=6I{&PJgJPP%ce_svkgN?`F8J}0>iY}!E(=2&$?n0GV1dIfkD6dY;NNa{!0 zJoFM4i`vZ0>@0Epm~zqxTP-*60C{dq4_yLdq!n^1%) z1jDAw8mcNnk2hJc76K}Gbj?ltxT?Z&l1GRHZi|Y1YPB^+eNPOh=te zcyv&m&^QgeWaS=EXsf;(Jm#a23Mdlae~YRk!XPOrA;Kb1xtI79@DL&EiR;Tm;EfQn z#&{I_ETBOsr#;#RUK%tQjkvr3!n!8+<)*BO=jDL82pg07P!7PDLFtCHn_)nOn#2t; zbUh4x>IQ=_D{Ry3${Z&oisAY+h#SY8ttK&z2;nDyxepH#?HgB|2NC6wbNjxtNTbJb z*mhzbI)2z>pxb&v9enGK^NWbi(Y16y&bhyo^L+aW*CB0c+MBHGjh@-F%U!#&Yge`|cWVo~wS{*p+jHCe!`z4Uo%+hoLuZG! zx^$yMH@bAQ1OM97j{WRQA#Ym0a-IEOTxa)2%PH5nUHjbD;=8Hsm5#kM$T?ZE^%qNg zI$LN};}yWd^d7lEGd%CDrdp@^4z@$;F^I3qKx1KWg0Au!xbR^^(P=RIs-h@;9Vw+x XX!@%@q3ExyZfUAhn)-&oNeR9K03~d- literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0013_alter_commander_date_commande_and_more.cpython-310.pyc b/gestion_produit/migrations/__pycache__/0013_alter_commander_date_commande_and_more.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..23ff87333d331124d454c679ed9844025e256ebf GIT binary patch literal 834 zcma)4yKdA#6rGoMZSQV21wujssx%f-97u~$kPvAgO*%Itvv<~vHTG=$2qG05v4@ zZ)Rx4GFI`7Q*umzgZM~5C{~IOJQF}qNfK;u4>?Jgiz{6;d8cjNx>038nRem7-5zsH zj&Qc;2#RDBNXCE`G~-H?0WjcdRE||xh9Dq-5k6xGA;OiYj3Hi!Fj-TWuCMvCfAV+! z<`*oRz#J9ty6E+_Qj|R}RO>~{Rb!#ooqKd}@c4<$O{W^UuvL}UfDz=Kx=AIj$;vj$ zMK=sL`;DSEV?s6)Y;!a9fWDK>9)eb1W0Fue>MnG>v>1&+E%V-V2}cjTZ?euS<-~x& zQY!;)XDDv;d6Vnb*7_3`IZ382lml5x7fVzGy-^rXr9A6%;|ur<)JkC!^+Kz*VW`2y z&wYC@ed)$4bI}XzZ^&KfkLolk2t8idS~=c#3m4m!`t^gqkmdny8{iVsx3*Ggi+-5Y z*g~V9XT3^Kk6)#Kn450zNQyQe{-@3RtM`q+q-ZH=?<0hSaq&Y0j54}M#rJI#UJlG8 rXzn4;MNsB-VfW$9(D=~oK-lWPiXM7)`1H!cXVf1w@&~b9dYAtM!WHL{ literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0013_alter_commander_date_commande_and_more.cpython-313.pyc b/gestion_produit/migrations/__pycache__/0013_alter_commander_date_commande_and_more.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..99e9ca89494e3c814b3a63e5c3df294c7740b0ea GIT binary patch literal 1293 zcmbtUL2DC16rSBpHoM!TO=Hy}RBJ3^2(+~#SSbauRB5Y7rg~Z!w%JJ--R!2bn~K$g zAoT1-@F(cSv&SBLOnOO~iw94+MWT1#q}@gXBik&+ys;5>cqfTBYJ*e}ONuypQE8y=cBaC%b zpOOE|XGY~|oaLG7Xdx%e2k~upQcwom|45aF^7cuc2X2E!qBuKyeU3O@L^&x3wVLC* zfLte{$0`9EsRf)0^VmaVesf`xzcU0eI>g@Mm@faD|0&#*8^-<=R)5y;7HcocA&kj;kU zNea+L2&ph0MjrF2AIM{u)+yBGml+MY%uQH#WW~!e8c#@rxdbKmbz#Wp5rd=*DYpZk z3at^9g%#9kJiKQK2_qQfGI64avyDbXLqfQmmL5Dv)bHN5ABU8O_Weip5)Ge4LEVmc zV0%H8K@T=O;K2R{%ST65zcTQgmM!F34R7qZvkClEWRt0Qw&>1yhj{(7xz zA@fYznAkTa4$kKfMkfz)g06knM-~08)y__}vQs}0D1CyTf6GWh literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0014_demander_user_alter_commander_date_commande_and_more.cpython-310.pyc b/gestion_produit/migrations/__pycache__/0014_demander_user_alter_commander_date_commande_and_more.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..425ec6c0e5e95e1f2048a214cba04516bc26abef GIT binary patch literal 1180 zcma)5OK;Oa5MDoHyGfe1P+G(h4pF5f1%wbns1?v2`na@Qag2UODB)ffEvlS-UT)B4KIAGrQmJ&V1i&(r9>$zR#~8@E;~)-&An@qdB%gBYQ>$ z7-)j^tH0LQDb|G%nSC>|`j*DF85m%GVql^f+8>R+4cY-~TQl0r_S?GjB0f%ooF{Q6 z?I-~h*-))r|5_Am(8#`$LDtuR(M=lYW4&+Cxt6*E?XU(GSm=aqXop@n2R78ECOA`t zse=n1VH(&Bn=l7;Xh0L@p#=*xGat5Kaq7U*RJ(@1b1VMtKkx=D6Mg~i!Af#h4d<~a`pA?C-JDN6iFnn1yGxkl?x{6OTG z`okoOf*8nyAjiwlr#U}LQj`v01(0TuVS0GBa`VCtojc+J+orSzB8cBhGcJUXE?r3q zV2)DHleR(XC`J4@h>#%4S|g4EqdjySvicR5FyCrTc~?s9Z}HgN=!#^_N&Vvjy9e95-5agYy?QTQYKo_%*LgQ6t^cz{I+N2> zJ!6MP_PBI(L)XmTrmbtbwxXH8OiOtWZ}B{ubH11R+qHC!cFWa@vJMP7)f4Vq@RmMO l>+a=x$$rUsdB7D1mA9_Y&dW;2R~ki`%F)pst)(p+e*n4?TpR!Z literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0014_demander_user_alter_commander_date_commande_and_more.cpython-313.pyc b/gestion_produit/migrations/__pycache__/0014_demander_user_alter_commander_date_commande_and_more.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..4a780fe9a213b26973e8cda93d00f293a19d56b6 GIT binary patch literal 1880 zcmb_dOK;mo5MELgMJlo_%Xa)y3S04^s!_-3(+-RRL82tE9i!070Rj+NP~uA6h9aFM zWi)P46e!ShFZ~bcEyo_+Q**R@k+41Vkdto;oZdT2T6P-=Xn}^1W@mPWv)|5qyF48k zNh5fExRqzGHH2PDqyHq&l+zthenJ>wWef3mRJaPZx|P_}xVD+($ptin3J53W5Y{ZM zoaraI7(Y(LI@cRYF?k}5ouVqzP1fLc$b2sldee8P8`LgdLTKX5IL)aNg@w3+5v;E8 z1Xgk4n#wgRIcz;Zqv52LDrf(mF4n=PW8E^#lY_qU=#aU~L*`}%=Wq%e>l!xK6M$)M z&=2dT@g=~NALg^h%I^%D#~D0=NAVcW;&GgVsD;6(a$#@|Pplhwa$WfsJX8M*&*is_ zN5j*AXK8RZP`epC8}H_t#wYL`pKQz*^TNE}XV8fOuK}mBb}RgXdLgT`T0||8SzTSd zPMF6+X1fqE)}Vpp9NFW((_*1m2LFe|c0e}98p?NLW6(%eR6sI8-YUmdeKz~Vj;@M3KAyOvmjJl36 z&ryhxf52cTDTGcg!A?(dQkYWQkYWu4Q@2!9RD>QLFt6@|mU3v_Zn>ctjncSmpW7_( zJ(h<^dE}r>fk@t$BZO!6DX;ngjUfFDM|4UUBr*sQX#xdsS}p}WL&%es?MlpGjS*63 zJP2LpQO}odhwf1*qE}-y;PUJXk(=Xi)gY0+1GQugZ;L(^y7Q&&HGH8uRaspq z5Hv>^xKtrKyW86$eN%QOdRdsap)0X!$Ss8os%A)e;CoagT47C?75Y^e$E5u|+P`3? z2nj-9M2*;C$XT@&(tr>y&(10Qk@)u34Qm%#8d&!}w{Fwmap><^A@?oUZ!loYlNPn` z-EHd)`dAm2m<2@o2zq?RAjyyaNUN2-r(6dRk&sLd@(NtdsHY?I{jRauOC~1u@3wmx zWKML9`D0_gJH6N)pYG;nI=QRIxvS5Xo>vYZ{PytIhn>=HyR_RWJ!+R8bxMtPsnJ8I zsoYgx!G(HHeU;M8bT1v{xpHh==}s5A;|o!q!f~$fY^}4ralE|oOXcu`L;m9Wi|SFi za`eDDqRkH7Z`1t_J!r#k`RjJ>o1wWD-&QWz-|Ts==c#sXEnaVNDyM(H$v^3rtC-@e zvVXHNk5-)OO8hNZ>63}SC;jHRKcZwr#JK2^1984jWuUPU6a6zTj~4U+1u~+SP!#1< eM@sg0wD1Rd_qCo^^dHlm>{2_s^d|x%%JCN`65hZ7 literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0015_remove_produit_seuil_rupture_and_more.cpython-310.pyc b/gestion_produit/migrations/__pycache__/0015_remove_produit_seuil_rupture_and_more.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..6830907fe811c6fb90feae0751ba908f933b398f GIT binary patch literal 1007 zcmZ`&J8u&~5Z=98+jnQ1gg`<`B+|GbP9!Lh5DHR68i)kxu323?6SLOct+RI*iL^lJ ziiW>H&A-`}$|WrlkJ)vc2ZELMyP4UU+4*Mnbibc4T3=sps(r!OH>X@*WMg}@t8D^c zz;l+mZ;Z<<-pPa_?V|5ib)FscgHLsxeYC7V`ma!Jc*$L5yZ3;=t7Sy$)pSY zSp>Ic99Cv7*7>jg)BpB={MX=)^M|{zzQ{5bX%9At(>)u%T5=&`D`Tu2EjcwB8dcjT zJ3G6NBw&%1fJQbIL6+BqBVAk=A*=CHmEIr1+x59BPc%s#z>}=W>p^H@axm^8*w%@{ z9PBNhG*@RPQtW?7cHI$GSpa_2HmzBk4sc zZ6b*0FM;^)G0B_(8wzWdlg r%iO1M8^a_k$9fx%eOo+x?{GzEA#FMD=;@-t&$zp~O%MgEd?Wk=r`;Y^ literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0015_remove_produit_seuil_rupture_and_more.cpython-313.pyc b/gestion_produit/migrations/__pycache__/0015_remove_produit_seuil_rupture_and_more.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..33595ca31f99d613ca36d902ad71e6088b9298ec GIT binary patch literal 1562 zcmb_c&u`O66dv1&B@n>X{#_vXDf!&1pc z@VvfVX0;qbe=B43X+jIeeC3H8@+Xq&pwHw|Hw(Gprk*jPq5=jwH9wD|CU z(a3a>YigDJzA}EU=+bVnrto6M!$_Jf?$aP@94D>hNr8>SNP2QFFv#1n2&?!zQhO5keiBg7Ckc6wc!7!ttZ72FnTXK?b9}eV+AzmbkvUvghVm)W`lTf zEZ9~O(})nU3|K?>kmOe{xpyIjk^9pxZjDC2#k}ptg1Z54GD!S`gu3|0o9-u7;2!q8 z3-xf3h?MoHNXSR|9T&ja_V2=kT~ndzD^i!pGc+(!@mFnN==0{|n*$pa=X%!4p0(0n zEca*2@AF2{9$4w<@jdH!e{mH?`_59&S>1D1|M;P|wz0Ri@#fCk3vb1{3-81(zO#GJ z-KDJ_?R06UM|ZmLu08BJkKPw@fR*hq#ya_}uuk@8SH@Vo>$R?PE!*(KykkDu6sJeA zSMuUJ&}GrT?}bf%*568#pXN9_A(f$Qenm~RHnNhsEY`q;dlW?{Knx5`(}pI}X8uB_ WKbXs!`P}Z!oa)Y;`UioL0{ja+cZ~D^ literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0016_alter_commander_date_commande_and_more.cpython-310.pyc b/gestion_produit/migrations/__pycache__/0016_alter_commander_date_commande_and_more.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..798e9cc36cde8e7d153fb3897efb4e05c8f5ec74 GIT binary patch literal 833 zcmZuvO^?$s5Vf78P11I|ClC^FKu9PYHp>CT0ii`g>;?9+w_L2ynFd!$+;x%)_6pbj z5Pl7JOPsjSzpxU5ah7hE4@Z8Pv7g7!&(@Pk%&5Kpeou`&#=g1adh;ncqTU=300UmK z%>6~lE0KxH%RJ7G8F=7-V&J1#_#eH@2Y$+uU_)!zNg`}qslw!~(sg48l?E)EnVY-b zrj#5}Z&n1zG7c;gzzd#v=q~~g;Nf5~#BdRU4*?8d2qAqDjYNwW;&lk4HHYzf%b)z0 zzxOY{5ZMT(qbM*gPkg+>6UG0Q06tr zN*lD%Oji|UXzT>?7Uecqn;~PH5uI{#(}BBy%~JyP<-v$0+z#4vRnIj=L%@07m2KjY zh0Zov=M`GN$6&6o1iRN4FV)KAs?oLjN<~hRu?=NUmeR(O6hT)a#bYVYy1aA+Tn4yA zl333aHb#&J8^0)9G_PD~Ll1)4=p~8oa~ry?T15&%hv&LR>viqS#(Igr@Aoq^cW7A; z7m&Ww6{ZdOQKqFX6xn&!VS0M}I{nMrboWG3a`}nOosKKhjQqpHE1M6NAB=mWWGQQI z6NF57{!c#;T=4tc|FMh0i=LST<`(g61dF^b^Z~r>58fZPC+zfJMt2=Me0FK!bM7`8 LxQ)aR literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0016_alter_commander_date_commande_and_more.cpython-313.pyc b/gestion_produit/migrations/__pycache__/0016_alter_commander_date_commande_and_more.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..983674d72de09254d2af1f8367561afebd6a495b GIT binary patch literal 1292 zcmbtUOK;Oa5MJAfV>?ZohNqBtg$f9jcvJ$lsH%iO1(kbnlzII5jG=4 z1)n#)G)QU&&VuSc3%xd%xq-|#1rK~VJRlFmJa{6GLh%Vn-r)EQON$NM8IumfocuK4 zh=&-vpL&6!Ky8GvrhqsJM99NP9s9h)G3&4)cnoSTrE@MwILxYOkW&Wx0^Vn!OG`yh z1SVxExe$e18fnsyPSoMq?CxMJPH>JJ%u5mwchZE%jDZ@KK0ZWt&YyK}#vEez(slO& zkMAW>$4ww|gQz921@}|#(u-HzE&Xsee;+P(<_z;xq8o(<_FLUIT64Vf2uut+5USPj zTNE$Is!8lQZPn1Xo6oMSI>g@Awe~JsdslWxy|rm{$Z literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0017_alter_commander_date_commande_and_more.cpython-310.pyc b/gestion_produit/migrations/__pycache__/0017_alter_commander_date_commande_and_more.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..06b329f215ef20ed0aa0f8034ec6434f2207b9b7 GIT binary patch literal 834 zcma)4J#W-N5Zy1|*}l76Di9LTKw}}DLjz5Of`mu`q)F#yWp4J&T5IpcACX84?fnq` z(zaCBQAa{B>yTXdC|GHqXV!0L-@IKro5cjjxA7w#b3(rQAC*uLOO>{YWYmK!4BPA^jBa+**-gRf zK@dE9@qf^ZXOBJh*z}Sz7Z09ti$w3fNxO|!5V6DVo8No$_I=FzCB00>La@52X=Z5% zeU(bQl1HGo0^mKu2rFxd%UxYlR#mR9YFwK_6DW_cb{^q`t(J}WyJnHKma3 zNcfWZj(i#I6r^&I&r*+a#9KEb;oxB zxlTlnRRT6r4>%R(v4_a~=E7wB&Jg72j7yP`LNbY!o+eO15qh-E{AvIw<_qYydtylgfy7T&~jfFhRhx@D9Vs>JMgK{ zno&hqL4(HRJxfR!0g)@ji6YK6nh^~N;gT&qc#&w_xn(~NDG%*?5A9_dK97Qi9r3{S zf*OMvY&NNl@2=Y?24W9>AU2HV#y^f`w()}NkhU-6tiw+r-lDFK%r&K}sbl)<^{$1? zGi_sX-tw7;r-_vr%IR-b`E=YsA;~WQ7N+~m@oT}XyV0Loe^Q5S%6mTa xpOKD6>5vOc{4%KU*MY)|AiA2OC_No1*)QnIcYRdR-&yVKOe;I{1A)>H@Dt^CM%@4a literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0018_alter_commander_date_commande_and_more.cpython-310.pyc b/gestion_produit/migrations/__pycache__/0018_alter_commander_date_commande_and_more.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..e332f86dc548219182559a4f8773658654dee8f4 GIT binary patch literal 839 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 literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0020_alter_commander_date_commande_and_more.cpython-313.pyc b/gestion_produit/migrations/__pycache__/0020_alter_commander_date_commande_and_more.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..94061530993f5811691a8ae7dd413cb66eb4e304 GIT binary patch literal 1298 zcmbtUO-vI(6rSB}x4YXGNVyc3KwxgmqkuDnthO9a zngFhskQ(D*^kPt3Q(190;=B*p{a!7e--??wk(eOzWH0_87 zwinbHG-9+SKGo$;B^4>qPZ_~!H`-@?mV4Q0B{Kam zQ`Y%F|DsehW)5aymR|xE{vRlm2KF^YQ93$Oa$nHp?|Pr2zqQ)AvF+U04+Kotz)!xN BM~(mh literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0021_commander_prix_achat_alter_commander_date_commande_and_more.cpython-310.pyc b/gestion_produit/migrations/__pycache__/0021_commander_prix_achat_alter_commander_date_commande_and_more.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..a650cc3ed9b76c4499659487e2e39147e8a5b63b GIT binary patch literal 1062 zcma)5!EVz)5Z$$%#CDUk6ljh_Y9(YL#epM2sFe^E5>%kxd|A1ft-F!!P1klsdxdNM zffLX_;NHL33kOcQaYjNg>$GV=MPen7XP#$wcHSGyPRA#>g5IY1NQkq$jmD!O^$u0pKoc9DAZjGIHcH{uvCqZL|d&pj3X+IN*ic2B$LN_xB zJS|4%+wxk&U>l#}BN|R33M8_CCN#3SGj4zdHgAqw;6MYKQwv&CgS&{khIcK&qalmak}EcnSr+Gj9>gVIgbXp3NyW9d$k6^oiMK2s9mS=hNXJ?4H3EIO zUqk&W7iBCI??1+(E#QZ7m6p1F!qtH+ILqUV2R4#!h^`~;7)&<~1y4bD{=Hd%x>Gk6(&P%b>oT@f3 z`^_A_IPYJ4=r5Yw3%c56_4OFjK0^|qN;&#%#_*)nT-ijxCmeapM}im1GS%H3faj(a zWt*`5A}@KuRSju>$Iw0Zy=O@E+;z>3OMxu7#-7QXYr85(+Lsf4Ih*H1ZQ_Bo`EeQ^ z$&7~uN|T1EOaw}MT=8&!_htB(&f)cVhp70&g}4eQ;Y!H=9D~8+RGFU+MIpryjY}-s z`Qv zI~zgZfP~=8g*!LWf6x=E)Ju=CFOKHY11H~t3^xwE*^QHyT7X1X_S^T~ym|A@d*9pP zK=~12gtcwN)mz`zwsfv<8QiF$d9;MEaRK3iuh*^7 z=Ck)(My~ThQ}c=gWqj!A(rL3M4+M*&M4Ih5q^+cJwh5t`6Jz*`rcU<}*D&Hb*0_Q7 z%Nj5E#d`Va4Y{tc0FqL@GIp(qOKOeT@VyK{;u}?RF4_poM{;rzQa(X~&#O`!qs29nQWW zLF3ava2;~*S8su%7QULfYH7qoz&Nd4fkR6n-3`)~kmWtfcjAPSC}>m905&QHW|k}{ zpDgY&+6v|5GXR)EKbU}122~}dlu%3?*dW-!6BBuwG{ruPc4JTDilA~TOVMI`JYY#2 zu?G+(-Fs;e3HH?Gc&e!NQSN?pzxL>-+UX_l!^l*mMKXYdNQXcf!n8#}FB1Z}S_(8+ z(}e6Yo`@EUXcVjEkaj4PGHNiIa5an4x)z2v)a^KoJd)-2BSD*#XD;bnQys{4`#MxV zS1ol3!JsgflKXK)rICt;bm9&j&G8%|iGZ1IkU$8|c2YqTLbxLS5dKJh_s$jnnXifDZRk>f?8B`hVkwfA+2LfhBLA5`qJJM$P|^)Vb98lAC}f z6N-z;pCG>zulZ!Pq!g`?`y(YeJVcfRkg^xTz$;PC3*uKUSv zrGo98ge~^0#Vo9rg)Q~mrGvNotDC*m%?Gz1u0Q0D*B|pkeEaZ@e@NSXy4R(9eY)R; z-|AOg_v^8_F22BAE6>2c({=CWM_!zB&2P83H!6o$ zNfMd2Ev>|k?8J#2iyRVgfPNuBxjm$xorr>UN;>Wo&ybUjt%F4Lv$zl{&2=qNz-8Vw zzQwhQ#xCysI|@!B3rJ*x)wd#t)1eDCIJ`Ej1I5RM8q_BgyveoCpZfx6EciTVLJNI9 z4~79O!7{ACDm;LP@CcE{unCVR9;{8QtGi76`hVj$?#K6O)Pg6-^r`lbuNflUgl=> z%SIqXre@;A`B$5CEL|(cBJC;E>cD$(DGR++T_eS17K>b^VvLa|oh9wD>WdlE0mG6( zDLLv*#xBZO8WzR^KH}Jbv@3X?*_cRsdjJQ9UFI0mKM;~vwhs18XJ)$p7P~T2J(Ir> zSQXF6u}Zmi%A%_SHR4w@{*7eM@wQ6*8iWIt@G!?N%22Alz|puUd3btw6yBMW@a8uO zabkAZLJOH`@GZd9em)>uqfeQsoGD?xjlv_gL;q6Owrp#~qJQpc&*qrXyr0$Sj+<@b pS?$9xPWx&L&Z;U^wW$Jbc+IpICfa*FtM?nrB(Is|_KLOU`~z?QM(O|n literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0022_fournisseur_nifp_fournisseur_rccm_and_more.cpython-313.pyc b/gestion_produit/migrations/__pycache__/0022_fournisseur_nifp_fournisseur_rccm_and_more.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..f63b8b978cc84f8c04f94b89eceddf937a1819ec GIT binary patch literal 1733 zcmbtUJ#5=X6h8ilBIO^+vK*;4j4FzOR&X1o1`5=HQPi>FwvH1Nx&#?Q;7W@p^=gWg zk7UrOOMwENyL9Z{ZXGjb3NqSWB;3-WlQ#uwr!IXbS(aQU84`kgeDB@6_xs)TXJ%3e zp2D?j>|Y(BzoamF5@$?*2bf-hEh(PO5tu<6{#j`a3^Ac9}1%xxYP@4<4p+V&V>FmMMk#~S1{r#R=9@Mio$g} zQJtRLFyv(}kV&$ddFfgLC$NE&*j(4KwXVI!N9wgcrttKHkL*ih&EQ$^F{)$2q=f9L z>Xiw_84J0maR$%fELQM5&Vg0ovQ>5QvJNk-oA}DQa#qu;^2xtdK7}{Sr=s&&{0>hy z7RyV*x-**kX%fl+9HbjGlqeuA9=I`!#Ai2dtbIgkL9^-jF6E$S-w~(wjS~^ai$F16 za-E2tiv-L`GvHKA)q|M(EDUMPh3>O@>t1_qLRXQhO1rQ}i+8`=X%*eLII&v1S=L2j z-*fx}*c^MFu;P{%I4+3-G5v`0{UD^ocbc@U0g5GZ2ND>AP9*A#dalrUt=7C4RceM& zt6N)lE=3jAd0}GaLS;<$>U0YFb()tXEeV`f#14K{QCSg2)MkD?050j$x)Xbmm>qcV z*dy++Fz{I$EPscCmk}lzq)UiM5$Km2dldL-LJniclO=$ZCZx`I76q=FV5 zT?Gq-gb`c|HR41OXZvwPLqhm6gy_SEM6`9&z8_K^+FyKSZ`1G~3R-r=1KSH443Kmf zQyYK2Xa5gY_V~K70bpxnV&X*N;etYr>KsqkTaUQ`p$9~wHq615^b_hC$og98X=={+ zVXv1$)_liYIx&~J`IYWmzMCy{vZa%3>9^b;+eh0EdI&X?P4xvr^S9I&N!?1l`IhAq zbGe%@b?1uXD4%pzH%?YJp4@x7_LM(gdwzIS#Ygua9=Tq}jgQ^9<32uyceQ<-{eCk1 zxv#5l81{6@-oTJbp6c9=pNR!UZ%6R6EJ=xyN+D0NRl)3*v zOULiomg;^04HAM`UoJ1fO8a?cJ9uoiqUa-`D zor0H6>XdHka(2kT1@8+351pC!*-bs*$1L`ja3Bfs!gv{fJL3#e^<|l zlzqDO83D4C14|v?Q=Yo$&3tgc#onxs!7Km|eCRdxm}>>CY)rDdySFDMs@0XOYizZs zVTVATJs7f>n_hD& ztBE414>-x%qKRFi*wQMhtVH8==uadTU^cr9h5V>9S*uEZr648%JTJi4SV4Pm6c0@x zI(H#VB&bkm3nY0U#7UbKHl)=6=j4D@F0s}QRb`@AMT7dlCeyS+%!F^Kr%tClBsP+2 z3M`(g3XR(~xf#4xs=%yTnMG=j=lk)E>BkhLgI|z*P$ecckya#yno1)6q{Za;@NIHq z3d!Y)*?Bw{nXT%ASuL&+eKCvi{FAmjPQ0`F89~4t*Zbr74tMxA_kQ1$B6HHP;cAsq>w!DS~a>4~)tUaY8n$!*G>P3dg$d+uLMX8iyF literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0023_alter_commander_date_commande_and_more.cpython-313.pyc b/gestion_produit/migrations/__pycache__/0023_alter_commander_date_commande_and_more.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..8760b6e8c60543b1ba8b489857965f0ee64ffe54 GIT binary patch literal 1432 zcmb_cJ#5=X6h4X)MKY2tGmhgX2pS7E8r49Yx-C!#MuD_}TR7@LxBRFI%MhIG1)R^%$U*ABIA|}owT`7yZ0Ss#!UirNe<+@_wMI=-|>6LX}#_e zY_+vj@z^BfPaPDka^g&P(D|KELXBGlbYHqbf2n%yw*(?WOOt}oHhFQeXuQ7Hn3nC4Q(L7^a0ZAH( zn8#92hkSq-JnjgdfUbDu-iT5TJ32p<^?-8|kD14q8r@VNOzImVI{?@NaTX$oR5OL@W=yo1P7e2E%-e%-&Da7g?wzx8kOkPp3&X8F!HJnNTT zc&|8Qs{$+ND<}LuhjkYdiZCT8r6wU8&06o>kAM@IHq47bD5LXpT+8Fs2qU Z8qdjfgc5M6&HaonV(P|8Pv8dM1xM1z16La0cH3JEGuFDMtw%}m1v+Z)#F3VMZW z{{rIL1Al;Pe*pItH%>WmM?x^`ByCa^iIsLT^Y-oR?wfH$v*|M$UmvdUZ#Bk#m|$|a z6s*zASIGbaD`9Q(YbRD}x9!wvI~H4K;DGy)fs1y}{ou4+ur^s(8PFcK5!%{Mc~{1Y zi!9gGQ~)M<$E;0`ISSTj=FDOYS=$2Ew!!LJZ3o?61#EDz+N+`0^T34)RB6`0gE}Gg zo)7+>2QzyXH1@{)=862-fAZ&uKLe*=9!~Gs6M4>*_yU}r!WZG(2tPlCUx16FJd?Ls zf=eZO8Lmv+aS4`7G#H~@uib#Fq}?@Le?HcX1f1()Zsd#lQb56#zIprhox4$-D3no0 zq-mT1c@Qf+3?ss#R7lkILxyfnQTTvrKA0iZ2j`8MH)fU$|MauLLQ7ZGF3+|Fc{RZ8 zxJXp!P&G{jqbyEQyQQscb4)y?0s^>R zLP3#n6?2Kf{m_=?Xx-RBxg~NO9&q|?5od}|yh{#Dnqra6%i-F=esJ(PIC`W9I21&C zUmon=8m(-EP3=YHbE8Q65fu%J1j%ni5nUlM z8k-2Pk5uQZ!!eh(ImUlvI^c;>UpfY;Kc*HaW9^x0C{9K4jNKI(YNt>gz3@WhT=5-z znknp#wrgMXarBMuGZ|8{()@zfYms6rr$$OziRf}_#J2^uHrJoEj&)`0=reCof8P7g z{#@<9m*#(ldXeR?$au_l+&^x`wrp#~a(^H98i&|Po`1MH?RnqJQ^JZ|p)+(HdU4hj jtFTo{S;|)uj@~}>ZWy-rU|5ugruXuyxuku{T6F#bf!u{& literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0024_alter_commander_date_commande_and_more.cpython-313.pyc b/gestion_produit/migrations/__pycache__/0024_alter_commander_date_commande_and_more.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..ab4b53f95a3a27ed44bb1fec02f6117008128274 GIT binary patch literal 2212 zcmb_cO>Epm6dv!dck{b$(uB65PFMu1C`}YVYTBq0q6#!ADC|&iz-4gOv&&Ggy&aEJ z2p}OLaYjg75l3=B;#hI2luK{y=CZ4~aNx8jf&zEm*xCFvNrOZ!d;H#;?|buR-g~n< zFpx*^{CcCve#;{Chf;b^dQaG00^xgv5!O}^SO3I{ww&OJ-t&#-6hKFrikr5Z5r`39RuX zPRwdNWu?pghY7K)Vu47q<>8a&tX#S0_s}$O(l~>&@aZ^*^MD#TG`%O5&mXtpz6Blk zFKBpRA^DVe2LD$)L(e>(VTfn^_-^1F3fREs77}OdXXI4=C_aBCe+-X5h5y`{{0sQv zsrx!PGvujFQ1XiOV~V>J=tT=>U;oC@xj^)rJ~He-K+C1G#G-)AF9zn)jer& z-wBzJ({pq4uMpc6l#_~IuiKsjl4A?HuM)74y3eW1?IYyC5eQTMyM3@mSLL=_P{SY$ z?1w-5QAv{-vBA8m4^q~lRXcP=DG6<;T90^koyt@+rmKv)jvS1fyKJ4?Ebu+{GdPj? z24|lVyYjIuIJ70&7+VE{>AVz~%+O=PW}KSWN(rvkm;LLMulWIu7clOJwkO!3eetda zuu!$uyYbxCrn&W_d9X>{q49x8y~hsE9f8MytxYQXs(#2l76dfpup3`cne83&V2@1# z;aBd3myh_cDOY77VCiTn+Q_}btpkx93F&ENB2@e}0By|#Pm=KvKkTxfDDaieVKoG7vWzdEQsWKi2mwD9l)wDw!6jJY17!A0(HD&&F zRTN7qAv~oFxtmZGkuG(WAi*GSx*9ipkIG~yDsp7i513%<^p+=RZI3SVeuMVz+ff3C z0C#VN*g|l&777{=!Y5&cUHFh}ym8IC6Hp#lZ>?H4X>d>Y4NGv}a{U^E;=LbI3%_~W zdZLo8gFD@Vntt^^*7TLeXFLPTMuTdS;5(>_Z_rK#=ech!CJ=E;~2A3h&QPMYhJfn#@!P^#eGN3>*bb#W6&+FWMsZx=Ci#dmD0SV>LllU zVtY0JinA8gYgD6gDpf7T_&EjC7vnCt!RJ9$Js+qB+(~MhwwpoP@bBp5zcaI1=G%OG OxY!yl{)0e?9Q+HwaVA;- literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0025_remove_demander_datedemande_and_more.cpython-310.pyc b/gestion_produit/migrations/__pycache__/0025_remove_demander_datedemande_and_more.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..f97f6ddd86ec48034a35af5131982453bb7e693f GIT binary patch literal 1065 zcmZuwJ8#rL5MDp-&i38q!6Q&0bP`dd6H*)@kSGvJq!VdK3evf;oSVsIPqz26wj+@i z+WQZbq~{;xA0W|eOLd~6p+Mp>yUybRS;@0AJForbTZ?WtV6+}M&-q7}v9H>gUv$Pc z=_}Sr00S#!k>2gp%IwI_oXD}*HUkIT_Y7RL$L>2Pa>3eT{l<)P*lyoeLB>ZiDY?iC z)yxE7S`4*sel3%+Nni1a1hU8i7TI8ptjIxk+yGnmnA)T_NpE0l?4dvQp$RSUz=weL zHk}0HHgu*QbYWp?!{StDcVG#YZ_KzgmvMV)&BfojG5+rV@gq0t!V2NNr~I7@oCJDt zgoTD2Po#i~m+JAx#*?RUl9njrp~$i%2ht!Z@zRXxEY5^PU#oeii< z53rX}ncmrl9_UI1*9dw=UGVG_=>jdlgQQAJ)j3AFFA6kw={r*Qkoq~P#sS9^lz)j* zb+5tX-@fSnQgf~rj4S2GGU0{D`495#_7{{Fo5FFdf|zCkRf?o{;`pdaQVm>NfD@!K z=0lE!v~{`m8_dKpzA`uPwg8MK9qscq$a9bGT5=kqr{#&rQ8`sPRKb=es16Fm1kc~? zDU*+=gb_dY!$Xl_SP)TZn2Hf6qK_&J_qJb$|F9ljJ^hgQe-=w~z4(G&!~eN)$^QD} zt<--W(O3U@9<+j4)quHM%y_g8(gdQJ1bo7{dwJ~WtNoa7_14*O<4W)LRe Z3Qw)A>S*spJ?WR0Zrvo|*-O@n^B0-JE`I<3 literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0025_remove_demander_datedemande_and_more.cpython-313.pyc b/gestion_produit/migrations/__pycache__/0025_remove_demander_datedemande_and_more.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..747435c11ac26ef26491fb560212bdad09c77182 GIT binary patch literal 1730 zcmbtUL2nyH6rSC+H@llSah$XH%pGvh+R zLGZn9++mM%2>q&z>6f1<T%4IFFh7hrl1@t)*abO%qpQM&zgOJs7W*4 zXW9Nc&`$vhcTUvfqAI^@Sp@oKIaHwkJFm@sRxqz9(?!iqax!YC@z#pesSr zp`gzZvYU7vwRNx-2-#sGiaRW%Ay@8z_9%2V^cjtWy3BI6MZ0{D-c3PS8$pn20v-?~ zZME--M*)c$^wm;wpNCW$N$g8!L!DU`V#)N~D~b z7$=Om-g_iWD4GgI!Dtm;qVLeiMD~_8GW2Ehn|mV%*-Ha!t#7RjSFR2h*N*ds?ToB+ z_EO)vl+M&kM;{B~2+rp>D5 z#T)9h?BFXeZ1d~Ec1oL+A6ZM)iDvO{t3Yc#Bjfwx9WbHGD7pe-WN4Z;Hj!5R1-l2!{W6+5EyBKzW}8IvN`|& literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0026_remove_demander_datedemiseadisposouhaite_and_more.cpython-310.pyc b/gestion_produit/migrations/__pycache__/0026_remove_demander_datedemiseadisposouhaite_and_more.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..e1eb9101cafbf9b314fbaef161247ad0ad358446 GIT binary patch literal 1169 zcmZ`&OK%e~5ca;3-8`C>M`?LTL7+k|O@#yk387Z1=!Nz`Iptz)GfwKTyH35k74!<% z9QX%Z`#Z{k1HZsmPLcQpNIYhCQ(B?clE*Wir@tAiX0yg{O+G!7%46(13FnuK!aDAB z6$vn~BG#kRj;z@3*|F1eEVjkK0rw*VSJ)%>gVS@t+GQPYiauWpa z6^JP9lkWUlKw%ws`VEO-JquXR25V^b9N~^UuqnsHM!tf)C#oY~1fu{dPz4_XsNq@1 zo7$)jjfoFUn48$pnviz`=3(JNk1OXqu1>6T_SY`7zkZ3m4U1^sgd4B~%Vpl7*PDZz zh{G)tY@fa#!DtOdN>K2zR*=igbk^1$J?2`(>QHbHahQP69KuY@1dca6R$3VURBe_> zzbUq5DmFG{I##O4BfH z5xI>-j=wZn$1;`dNG1c7ui)J#Mrwm-Q>6CE=XMb)mGq+aEa1s8RZ#^o2=gd2jYFaL z6y~K;I*tx7il#)y8%Pm>3HmB7Uu~L2p{KH3{z~~Z&4!sPRFOQ?p-fdG@1f4rW0lDP zf;Y(1H-=$aZ!Zdyw}s12r)7Lzq~+YyIARESB#>`#evpR|6+{w z(T)x+(TJ>PBiPaY7Dq(cRs8)%|Z=x@Ui>i-YszvcbXjgk^7LUH&&ktK;{Y z{xvq8rB9Lg%y!&Au4h}e<^FbEI#(?BS9x>)09&s&SmUj^7u00000 literal 0 HcmV?d00001 diff --git a/gestion_produit/migrations/__pycache__/0026_remove_demander_datedemiseadisposouhaite_and_more.cpython-313.pyc b/gestion_produit/migrations/__pycache__/0026_remove_demander_datedemiseadisposouhaite_and_more.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..66c18bba338b845e537f994f6036a79548fadb1a GIT binary patch literal 1902 zcmb_cO>7%Q6rSC+owXCkj*~V{Qm1aH5LQHLMJmEogoua=q$xt4R9qH~Hr`n?biM1& z?xxU!goMNm2@c#j(i=yPmC7N<*cV%K;lRl^M}|9Zc5Q0WR0!IY{bt_0zi-}rGox%a zgW&u2`x^6-2>mXV$p?D$jc&s51HuR^w-A@3dP~_?xw@}$t&ECj17U3y;e?^q^>NJ9 za9xWPo@gqSt6iLB4%Wf1d` z$zjLbWWMLJSHLD_TVB9yXr3MVheEbDdE}Vx-6-S{-0%gVlc+EuB152yR_IWe&k=Gj zG#v>Ev>YKe<9^^Um%5%bTeMB#9NY$@K9^62n5{=AbTfji?^;$g;|Xa?%dU(q5@x`l z^}3V~JeLYB3>qS{>jad?PU%DXSrAV%UYkxHpbLcf0X#+xVg>64`%SLFgMaOriAq%1~36QePbmGbp{-)7QKDdVl#!e_``1siiYR zJz8Ds>TA(zwO=Uq3LD+R#!qkdHg~$4JHH%0-hRwawomvezH|D~$EUX2v+sB8`#t+% z2Y#Dh3=uj|1N97{#ZWz)NkG=PR;jC(`pX;rh4TN%+9`Z_ZmugYD;M-&{b{bHpLwTn zBd%CkDWtyM=dVv%T1j$wxkTFf)O4HPmUR@7E@D^Qcu9iTe@i;*J292t;#E-LERcU0 i#86WdWt2in{x|g6AF0bq>bp!Yf3=gp`X>SBy9e^5@amxnfMjv)k&qk4=g5fbS_=*b70B0^@cJXbt!YEy1v&+DXbIe2Ic(;>NGzXgA za`pG}sZE4eg|L~RZeUPI`b3D6p;9i$S%6C z-xaq8Ra|dbK_h!6DhK9@_0`C(%&R%gmmiH=^D*7dQI`ZEkN!k)$U?TsqTjc*d-N~) z>2vaty}xQ}?z@_=n=%jSA)8+M;K0-4De-yN4X(5;7o9v`5&eQWBqN6;+++{g`kf_IB=Wq|0%AOaaM0yz#qT+9L_QW%06G#UL?G8BP?5yUS?{fzwFRQ=-o zqSPGyoc#36;*!k5(p3FmcOU)qR3IlmFTS8CKczIYL_aq(y(keRQmh{zpP83g5+AQu XPv@#i>Qb zF(Lk;L9Pk`&M_{j#n~nK1u-Q>`7t^9>6yhPnT4gPF~ROWG3lv5PJUi|K~a86X=X`G zZf1H>B1oh-CO$qhFS8^*Uaz3?7KcqPP(CNsu80+A2gnV@AjU^#Mn=XWW*`dy8P_oY literal 0 HcmV?d00001 diff --git a/gestion_produit/models.py b/gestion_produit/models.py new file mode 100644 index 0000000..e1252dd --- /dev/null +++ b/gestion_produit/models.py @@ -0,0 +1,142 @@ +"""Modèles de l'application gestion_produit.""" + +from django.db import models +from django.utils import timezone + +from authentification.models import Profile + +class Categorie(models.Model): + """Modèle représentant une catégorie de produit.""" + + categorie = models.CharField(max_length=255, unique=True) + + def __str__(self): + """Retourne le nom de la catégorie.""" + return self.categorie + + +class Produit(models.Model): + """Modèle représentant un produit.""" + + CONDITIONNEMENT_CHOICES = ( + ("boite", "Boite"), + ("paquet", "Paquet"), + ("piece", "Pièce"), + ("rouleau", "Rouleau"), + ("carton", "Carton"), + ) + + libelle = models.CharField(verbose_name="Libellé", max_length=255) + quantite_stock = models.PositiveIntegerField( + verbose_name="Quantité actuellement en stock" + ) + conditionnement = models.CharField( + verbose_name="Conditionnement du produit", + max_length=255, + choices=CONDITIONNEMENT_CHOICES, + ) + seuil_pre_rupture = models.PositiveIntegerField( + verbose_name="Seuil de pré-rupture" + ) + image = models.ImageField( + upload_to="produit_image/", + blank=True, + null=True + ) + categorie = models.ForeignKey(Categorie, on_delete=models.CASCADE) + + def __str__(self): + """Retourne le libellé du produit.""" + return self.libelle + + +class Demander(models.Model): + """Modèle représentant une demande de produit.""" + + user = models.ForeignKey( + Profile, + on_delete=models.SET_NULL, null=True, blank=True + ) + produit = models.ForeignKey(Produit, on_delete=models.CASCADE) + quantite = models.PositiveIntegerField( + verbose_name="Quantité demandée", + default=1 + ) + motifs = models.TextField(verbose_name="Motif") + date_de_mise_a_dispo_souhaite = models.DateField( + verbose_name="Date de mise à disposition souhaitée", + default=timezone.now + ) + a_rendre = models.BooleanField(default=False) + rendu = models.BooleanField(default=False) + date_rendu = models.DateField(blank=True, null=True) + valider_par_chef = models.BooleanField(default=None, null=True) + valider_par_logisticien = models.BooleanField(default=None, null=True) + motif_refus = models.TextField(default="", blank=True) + livrer = models.BooleanField(default=False) + + def __str__(self): + """Retourne une représentation textuelle de la demande.""" + return f"Demande de {self.produit.libelle}" + + +class Fournisseur(models.Model): + """Modèle représentant un fournisseur.""" + + nom_entreprise = models.CharField( + max_length=100, verbose_name="Nom de l'entreprise" + ) + rccm = models.FileField( + verbose_name="Le RCCM du fournisseur :", + upload_to="fournisseur/rccm/", + blank=True, + null=True, + ) + nifp = models.FileField( + verbose_name="Le NIFp du fournisseur :", + upload_to="fournisseur/nifp/", + blank=True, + null=True, + ) + nom_prenom_representant = models.CharField( + max_length=255, verbose_name="Nom et prénom du representant" + ) + fonction = models.CharField( + max_length=20, + verbose_name="Fonction du représentant" + ) + telephone = models.CharField( + max_length=25, verbose_name="Téléphone du représentant" + ) + email = models.EmailField(verbose_name="Adresse e-mail") + note = models.PositiveIntegerField(default=0) + categorie = models.ManyToManyField( + Categorie, verbose_name="Catégorie de produit fourni" + ) + + def __str__(self): + """Retourne le nom de l'entreprise du fournisseur.""" + return self.nom_entreprise + + +class Commander(models.Model): + """Modèle représentant une commande de produit.""" + + produit = models.ForeignKey(Produit, on_delete=models.CASCADE) + fournisseur = models.ForeignKey(Fournisseur, on_delete=models.CASCADE) + prix_achat = models.PositiveIntegerField( + verbose_name="Prix d'achat unitaire :", default=0 + ) + quantite_commander = models.PositiveIntegerField( + verbose_name="Quantité à commander", default=1 + ) + date_commande = models.DateField(default=timezone.now) + date_livraison = models.DateField(default=timezone.now) + livrer = models.BooleanField(default=False) + + def __str__(self): + """Retourne une représentation textuelle de la commande.""" + return ( + f"Commande de {self.quantite_commander} x {self.produit.libelle} " + f"chez {self.fournisseur.nom_entreprise}" + ) diff --git a/gestion_produit/templates/gestion_produit/index.html b/gestion_produit/templates/gestion_produit/index.html new file mode 100644 index 0000000..39141d3 --- /dev/null +++ b/gestion_produit/templates/gestion_produit/index.html @@ -0,0 +1,325 @@ +{% extends "BASE.html" %} +{% load static %} +{% load tags_personnaliser %} + +{% block page_titre %} SGL - Gestion des produits {% endblock %} + +{% block "contenu" %} +
+
+

MES DEMANDES

+ +
+
+ +
+ {% for demande in mes_demandes %} +
+ {% if demande.produit.image %} + + {% else %} + Image par défaut + {% endif %} +
+
{{ demande.produit.libelle }}
+

+ {{ demande.user.user.first_name }} {{ demande.user.user.last_name }}
+ +

+ +
+
+ {% empty %} +

Aucune demande en cours.

+ {% endfor %} +
+ +
+
+

LISTE DES PRODUITS

+
+ {% if user|has_group:"Logisticien" %} + Rapport de mouvement de stock + + + {% endif %} +
+
+
+ +
+
+ +
+
+ +
+
+ +
+ {% for produit in page_obj %} +
+ {% if produit.image %} + {{ produit.libelle }} + {% else %} + Image par défaut + {% endif %} +
+
{{ produit.libelle }}
+ + {% if user|has_group:"Logisticien" %} +

+ + Quantite en stock: {{ produit.stockActuel }} +

+ + {% endif %} + +
+
+ {% empty %} +

Aucun produit disponible.

+ {% endfor %} +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +{% endblock %} + +{% block "js" %} + +{% endblock %} \ No newline at end of file diff --git a/gestion_produit/templates/gestion_produit/mouvement_stock.html b/gestion_produit/templates/gestion_produit/mouvement_stock.html new file mode 100644 index 0000000..261ec6b --- /dev/null +++ b/gestion_produit/templates/gestion_produit/mouvement_stock.html @@ -0,0 +1,28 @@ +{% extends "BASE.html" %} +{% load static %} + +{% block page_titre %} SGL - Mouvement de stock {% endblock %} + +{% block "contenu" %} +

MOUVEMENT DE STOCK

+ +
+
+ + +
+
+ + +
+
+
+ +{% endblock %} + +{% block "js" %} + +{% endblock %} \ No newline at end of file diff --git a/gestion_produit/tests.py b/gestion_produit/tests.py new file mode 100644 index 0000000..de8bdc0 --- /dev/null +++ b/gestion_produit/tests.py @@ -0,0 +1,3 @@ +from django.test import TestCase + +# Create your tests here. diff --git a/gestion_produit/urls.py b/gestion_produit/urls.py new file mode 100644 index 0000000..ac42dea --- /dev/null +++ b/gestion_produit/urls.py @@ -0,0 +1,70 @@ +"""Gerez des urls de l'application gestion_produit.""" + +from django.urls import path +from . import views + +app_name = "gestion_produit" + +urlpatterns = [ + path( + "", + views.index, + name="index" + ), + path( + "liste-categories", + views.liste_categories, + name="liste-categories" + ), + path( + "enregistrerProduit", + views.enregistrer_produit, + name="enregistrement_produit" + ), + path( + "enregistrerCommande", + views.enregistrer_commande, + name="enregistrement_commande" + ), + path( + "enregistrerDemande", + views.enregistrer_demande, + name="enregistrement_demande" + ), + path( + "update-demande", + views.update_statut, + name="update-demande" + ), + path("liste-demandes", views.liste_demandes, name="liste-demandes"), + path( + "liste-produit", + views.recuperer_liste_produit, + name="liste_produit" + ), + path( + "enregistrement-categorie", + views.enregistrer_categorie, + name="enregistrement_categorie", + ), + path( + "mouvement-de-stock", + views.mouvement_stock, + name="mouvement-de-stock" + ), + path( + "rapport-mouvement-stock", + views.rapport_mouvement_stock, + name="rapport-mouvement-stock", + ), + path( + "recuperer-fournisseur-categorie/", + views.recuperer_fournisseur_par_categorie, + name="fournisseur_categorie", + ), + path( + "detailDemande//", + views.detail_demande, + name="detail_demande" + ), +] diff --git a/gestion_produit/views.py b/gestion_produit/views.py new file mode 100644 index 0000000..e932113 --- /dev/null +++ b/gestion_produit/views.py @@ -0,0 +1,522 @@ +"""Views pour la gestion des produits.""" + +from django.shortcuts import render, redirect +from django.core.paginator import Paginator +from django.db.models import Sum + +from django.views.decorators.csrf import csrf_exempt +from django.contrib.auth.decorators import login_required + +from django.http import JsonResponse + +from .models import ( + Categorie, + Produit, + Demander, + Fournisseur, + Commander +) + +from .forms import ( + EnregistrementProduit, + EnregistrementCategorie, + CommanderProduit, + DemanderProduit, +) + +PRODUIT_NON_A__RENDRE = False +PRODUIT_NON_RENDU = False + + +def gestion_affichage_demande( + request, + option_validation_chef, + ordre_inverse=False + ): + """Affichez les demandes de produit selon le profil de l'utilisateur. + + Parameters + ---------- + request : HttpRequest + La requête HTTP entrante. + option_validation_chef : bool or None + Filtre pour la validation par le chef de département. + 1- True : demandes validées par le chef. + 2- False : demandes non validées par le chef. + 3- None : demandes en attentes. + ordre_inverse : bool, optional + Si True, les demandes sont triées par ordre décroissant, + par défaut False. + + Returns + ------- + QuerySet: + Ensemble des demandes filtrées selon les critères spécifiés. + + """ + mes_demandes = Demander.objects.filter( + valider_par_chef=option_validation_chef, user=request.user.profile + ) + demandes_departement = None + + if request.user.profile.chef_departement: + demandes_departement = Demander.objects.filter( + valider_par_chef=option_validation_chef, + user__departement=request.user.profile.departement, + ) + + if ordre_inverse: + return ( + (mes_demandes | demandes_departement).order_by("-id") + if demandes_departement + else mes_demandes + ) + return ( + (mes_demandes | demandes_departement) + if demandes_departement + else mes_demandes + ) + + +@login_required(login_url="login") +def index(request): + """Gérer le rendu de la page d'accueil de la gestion des produits. + + Parameters + ---------- + request : HttpRequest + La requête HTTP entrante. + + Returns + ------- + HttpResponse + La réponse HTTP contenant la page rendue. + + """ + liste_produit = Produit.objects.all().order_by("-id") + + liste_categorie = Categorie.objects.all().order_by("categorie") + + liste_produit_finale = [ + calcul_stock_produit(produit) for produit in liste_produit + ] + + pagination = Paginator(liste_produit_finale, 8) + + page_number = request.GET.get("page") + page_obj = pagination.get_page(page_number) + + return render( + request, + "gestion_produit/index.html", + { + "formulaireEnregistrementCategorie": EnregistrementCategorie, + "formulaireEnregistrementProduit": EnregistrementProduit, + "formulaireCommanderProduit": CommanderProduit, + "formulaireDemanderProduit": DemanderProduit, + "mes_demandes": gestion_affichage_demande( + request, option_validation_chef=None + ), + "page_obj": page_obj, + "liste_categorie": liste_categorie, + }, + ) + + +def liste_categories(request): # noqa: ARG001 + """Récupère et renvoie la liste des catégories de produits au format JSON. + + Parameters + ---------- + request : HttpRequest + La requête HTTP entrante. + + Returns + ------- + JsonResponse + Réponse JSON contenant la liste des catégories de produits. + + """ + mes_categories = [ + {"categorie": categorie.categorie} + for categorie in Categorie.objects.all() + ] + + return JsonResponse(mes_categories, safe=False) + +@login_required(login_url="login") +@csrf_exempt +def enregistrer_produit(request): + """Enregistre un nouveau produit à partir des données POST. + + Parameters + ---------- + request : HttpRequest + La requête HTTP entrante. + + Returns + ------- + JsonResponse + Réponse JSON indiquant le succès ou l'échec de l'enregistrement. + + """ + if request.method == "POST": + p = EnregistrementProduit(request.POST, request.FILES) + if p.is_valid(): + p.save() + return JsonResponse( + {"success": True, "message": "Produit enregistré avec succès"} + ) + return JsonResponse( + { + "success": False, + "message": "L'enregistrement du produit a échoué", + } + ) + + return redirect(index) + + +@login_required(login_url="login") +def enregistrer_commande(request): + """Enregistrez une nouvelle commande de produit.""" + if request.method == "POST": + form = CommanderProduit(request.POST) + if form.is_valid(): + form.save() + + return redirect("gestion_produit:index") + + +@login_required(login_url="login") +def enregistrer_demande(request): + """Enregistrez une nouvelle demande de produit.""" + if request.method == "POST": + form = DemanderProduit(request.POST) + if form.is_valid(): + ma_demande = form.save(commit=False) + ma_demande.user = request.user.profile + if request.user.profile.chef_departement: + ma_demande.valider_par_chef = True + + ma_demande.save() + return redirect("gestion_produit:index") + + +@login_required(login_url="login") +def liste_demandes(request): + """Retournez la liste des demandes de produits au format JSON.""" + liste_demandes = gestion_affichage_demande( + request, option_validation_chef=True, ordre_inverse=True + ) + les_demandes = [ + { + "dateDemande": demande.date_de_mise_a_dispo_souhaite, + "produit": demande.produit.libelle, + "motifs": demande.motifs, + "a_rendre": demande.a_rendre, + "dateDeMiseADispoSouhaite": demande.date_de_mise_a_dispo_souhaite, + "valider_par_chef": demande.valider_par_chef, + "valider_par_logisticien": demande.valider_par_logisticien, + "motifs_refus": demande.motif_refus, + } + for demande in liste_demandes + ] + + return JsonResponse(les_demandes, safe=False) + +@login_required(login_url="login") +def detail_demande(request, id_demande): + """Renvoyez les détails d'une demande spécifique de produit.""" + detail_demande = Demander.objects.get(id=id_demande) + + demande = { + # "image": detail_demande.produit.image.url, + "detailNom": detail_demande.produit.libelle, + "detailCategorie": detail_demande.produit.categorie.categorie, + "detailmotif": detail_demande.motifs, + "detailDeMiseADispo": detail_demande.date_de_mise_a_dispo_souhaite, + "detailARendre": detail_demande.a_rendre, + "chef_departement": request.user.profile.chef_departement, + } + + return JsonResponse(demande) + +@login_required(login_url="login") +@csrf_exempt +def update_statut(request): + """Met à jour le statut d'une demande de produit. + + Parameters + ---------- + request : HttpRequest + La requête HTTP entrante. + request.id : int + L'ID de la demande à mettre à jour. + request.action : str + L'action à effectuer ('confirmer' ou 'refuser'). + request.emetteur : str + L'émetteur de la demande ('chef' ou 'logisticien'). + request.motif_refus : str + Le motif de refus (si applicable). + + Returns + ------- + JsonResponse + Réponse JSON indiquant le succès ou l'échec de la mise à jour. + + """ + if request.method == "POST": + produit_id = request.POST.get("id") + action = request.POST.get("action") + emetteur = request.POST.get("emetteur") + motifs = request.POST.get("motif_refus") + + try: + demande = Demander.objects.get(id=produit_id) + except Demander.DoesNotExist: + return JsonResponse( + { + "success": False, + "message": "Demande introuvable" + }, + status=404 + ) + + if action == "1": + if emetteur == "chef": + demande.valider_par_chef = True + elif emetteur == "logisticien": + demande.valider_par_logisticien = True + elif action == "0": + if emetteur == "chef": + demande.valider_par_chef = False + elif emetteur == "logisticien": + demande.valider_par_logisticien = False + demande.motif_refus = motifs + + else: + return JsonResponse( + {"success": False, "message": "Action invalide"}, status=400 + ) + + demande.save() + return JsonResponse({"success": True, "message": "Statut mis à jour"}) + return JsonResponse( + {"success": False, "message": "Méthode non autorisée"}, status=405 + ) + + +@login_required(login_url="login") +def recuperer_liste_produit(request): + """Récupèrez et renvoyez la liste des produits paginée. + + Parameters + ---------- + request : HttpRequest + La requête HTTP entrante. + + Returns + ------- + HttpResponse + La réponse HTTP contenant la page rendue avec la liste des produits. + + """ + liste_produit = Produit.objects.all().order_by("-id") + pagination = Paginator(liste_produit, 8) + + page_number = request.GET.get("page") + page_obj = pagination.get_page(page_number) + + return render( + request, + "gestion_produit/index.html", + {"page_obj": page_obj} + ) + +@login_required(login_url="login") +@csrf_exempt +def enregistrer_categorie(request): + """Enregistrez une nouvelle catégorie de produit. + + Cette vue est appelée via une requête AJAX avec la méthode POST et + enregistre une nouvelle. + + Parameters + ---------- + request : HttpRequest + La requête HTTP entrante. + + Returns + ------- + JsonResponse + Réponse JSON indiquant le succès ou l'échec de l'enregistrement. + + """ + if request.method == "POST": + categories = EnregistrementCategorie(request.POST) + if categories.is_valid(): + categories.save() + return JsonResponse({"success": True}) + return JsonResponse({"success": False}) + return None + +@login_required(login_url="login") +def recuperer_fournisseur_par_categorie(request, id_produit): # noqa: ARG001 + """Récupèrez les fournisseurs associés à la catégorie d'un produit donné. + + Parameters + ---------- + request : HttpRequest + La requête HTTP entrante. + id_produit : int + L'ID du produit dont on veut récupérer les fournisseurs. + + Returns + ------- + JsonResponse + Réponse JSON contenant la liste des fournisseurs associés à la + catégorie du produit. + + """ + produit = Produit.objects.get(id=id_produit) + fournisseur = Fournisseur.objects.filter(categorie=produit.categorie) + + produit_founisseur = [ + { + "id": fournisseur_produit.id, + "nom_fournisseur": fournisseur_produit.nom_entreprise, + } + for fournisseur_produit in fournisseur + ] + + return JsonResponse(produit_founisseur, safe=False) + + +# @login_required(login_url="login") +def calcul_stock_produit(produit): + """Calculez le stock actuel d'un produit donné. + + Parameters + ---------- + produit : Produit + L'instance du produit pour lequel calculer le stock. + + Returns + ------- + dict + Dictionnaire contenant les détails du produit et son stock actuel. + + """ + quantite_livrer = ( + Commander.objects.filter(livrer=True, produit=produit).aggregate( + Sum("quantite_commander") + )["quantite_commander__sum"] + or 0 + ) + produit_demander_a_rendre = Demander.objects.filter( + produit=produit, + valider_par_logisticien=True, + ) + + quantite_produit_sortis = 0 + + for produit_demander in produit_demander_a_rendre: + if ( + (produit_demander.a_rendre and produit_demander.rendu is False) + or produit_demander.a_rendre is False + ): + quantite_produit_sortis += produit_demander.quantite + + ## Stock actuel = Quantite initiale + total livrer - quantiteSorties + stock_actuel = (produit.quantite_stock + + quantite_livrer + - quantite_produit_sortis) + return { + "id": produit.id, + "libelle": produit.libelle, + "quantite_stock": produit.quantite_stock, + "conditionnement": produit.conditionnement, + "seuil_pre_rupture": produit.seuil_pre_rupture, + "image": produit.image, + "categorie_id": produit.categorie_id, + "stockActuel": stock_actuel, + } + +@login_required(login_url="login") +def mouvement_stock(request): + """Rendez la page de mouvement de stock. + + Parameters + ---------- + request : HttpRequest + La requête HTTP entrante. + + Returns + ------- + HttpResponse + La réponse HTTP contenant la page rendue. + + """ + return render(request, "gestion_produit/mouvement_stock.html") + +@login_required(login_url="login") +def rapport_mouvement_stock(request): + """Générez un rapport de mouvement de stock basé sur les filtres donnés. + + Parameters + ---------- + request : HttpRequest + La requête HTTP entrante. + request.GET["dateFiltre"] : str + La date de filtre au format "YYYY-MM". + request.GET["typeFiltre"] : str + Le type de filtre ("entree" ou "sortie"). + + Returns + ------- + JsonResponse + Réponse JSON contenant le rapport de mouvement de stock. + + """ + mes_commandes = [] + date_filtre = request.GET["dateFiltre"] + annee, mois = date_filtre.split("-") + type_filtre = request.GET["typeFiltre"] + + if type_filtre == "entree": + mes_commandes.extend([ + { + "produit": commande.produit.libelle, + "categorie": commande.produit.categorie.categorie, + "conditionnement": commande.produit.conditionnement, + "fournisseur": commande.fournisseur.nom_entreprise, + "date_commande": commande.date_commande, + "date_livraison": commande.date_livraison, + "quantite_commander": commande.quantite_commander, + } + for commande in Commander.objects.filter( + date_livraison__year=annee, + date_livraison__month=mois, + livrer=True + ) + ]) + + elif type_filtre == "sortie": + mes_commandes.extend([ + { + "produit": demande.produit.libelle, + "categorie": demande.produit.categorie.categorie, + "conditionnement": demande.produit.conditionnement, + "date_demande": demande.dateDemande, + # "date_mise_a_dispo": commande.date_commande, + "quantite_demander": demande.quantite, + } + for demande in Demander.objects.filter( + dateDemande__year=annee, + dateDemande__month=mois, + valider_par_logisticien=True, + ) + ]) + + return JsonResponse(mes_commandes, safe=False) diff --git a/gestion_vehicule/__init__.py b/gestion_vehicule/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/gestion_vehicule/__pycache__/__init__.cpython-310.pyc b/gestion_vehicule/__pycache__/__init__.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..d50bbbac073794ef15358d7baeecaf1f654297e0 GIT binary patch literal 148 zcmd1j<>g`kf_KYrXMpI(AOaaM0yz#qT+9L_QW%06G#UL?G8BP?5yUTZ{fzwFRQ=-o zqSPGyoc#36;*!k5(p3FmcOU)qR3IlmFTN}_BQv=)CsjW_J~J<~BtBlRpz;=nO>TY) PP|yx!U@;SrU||3NaR4IC literal 0 HcmV?d00001 diff --git a/gestion_vehicule/__pycache__/__init__.cpython-313.pyc b/gestion_vehicule/__pycache__/__init__.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..903dcac147659ff3fb5fb68f9fc13168159f12eb GIT binary patch literal 170 zcmey&%ge<81n-vL&H&MmK?DpiLK&Y~fQ+dO=?t2Tek&P@n1H;`AgNoP&Q>v@#i>Qb zF(Lk;L9Pk`&M_{j#n~nK1u-Q>`7t^9>6yhPnT4gPF~ROWG3lv5PJUi|S!zaRa%oO# rOniK1US>&ryk0@&Ee@O9{1l*|T@fqLWRT6pAjU^#Mn=XWW*`dy=*}## literal 0 HcmV?d00001 diff --git a/gestion_vehicule/__pycache__/admin.cpython-310.pyc b/gestion_vehicule/__pycache__/admin.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..aa6b50d9ace64e5dc0c69e3a85fe414b767083bd GIT binary patch literal 189 zcmd1j<>g`k0-G+&On)H#7{oyaOhAqU5Elyoi4=wu#vF!R#wbQch7_h?22JLdKv4!w z##^k3DY=<>ews|T_)@YG^V0M6lJoOQiZYXmKnAR2C}IIpVB(jFenx(7s(x{PQEHBU zPJVi3aY<%jX{vs(yN`Z)Dv*<(7hjf|k(peYld2CkR F1^~gcEkytT literal 0 HcmV?d00001 diff --git a/gestion_vehicule/__pycache__/admin.cpython-313.pyc b/gestion_vehicule/__pycache__/admin.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..78d7b067071eef818b245207b9bbbc997fcf2791 GIT binary patch literal 208 zcmey&%ge<81U6lknf^ffF^B^LOi;#W0U%>4Loh=yqc?*WV-ceQLpqZt^GlGlCgUyE z#FX63JU>mQTYM>5iFxVyddc~DB}JJ@Ma)12D;Yk6)ZKD$wu%WYPAw{q@d$`%JqGLuVlQe(iT>lIYq;;_lhPXUV9 a6>$I!WCY@35aR0H7u11D3|Xwub5ny8r*VS>Yk8Tzl2;~P zfr)bxiHei%e1G3}=hLH6pP;-xUdcVaUoJQlAA`TS$umo6J{%Q@g&xA zSu4>}eVoHfT4Xwc=P1`8l!FBx_Opt%J?Oo((uJ(p+$E`R+0Y+y zzNu5yRZc;y(pqhKid=lvkom5*CzU%-V}35>>U?IZn&c zMCE(M5bkbhj?e_ervYtp^N`s=_Z`<;d2WvD{+rl(1I*drx?TOoUC%heAsMq@>d0^; literal 0 HcmV?d00001 diff --git a/gestion_vehicule/__pycache__/apps.cpython-313.pyc b/gestion_vehicule/__pycache__/apps.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..b8a132577a8f5112f5890ffb603b3f9d5711e527 GIT binary patch literal 547 zcmZ8eO-~d-5bd6sT^Dd83K%tF)Pu=f_C`XCksw6;3Nd!{)JbL7=^Yz}>7lxZ1g<3f z0}}rN|Ar&!#FHm(CaZU=nc-p|s$S*Qd#UQ04u`Xh-rkp0eNOpTC~jV_1Jf4-&X{0= ze`Fsx@~7+pd(K4kh>2M8mALK0s7TV@RVY&KXV&X_!&DPpj9a>myep=U37j#>kPC*9 z;24Vt6A@!iB-k%{Y2PnxDeJVUzNzne+?1-dyGlrTyqxc5RbfW?&S>A{s#?V zd8<{K`}v}k!eOU9XWQv5KLDt*eFflW0Z2!tgl_{JG+Eg(cK{|Dtt)k?qAL=pKRj%4Zoeney;nIAjWW% rRvyM_8}AbGgIDe1uW^COa1Xmk;djhA|H+>H=|}v@kN1BWrEAqcR_2sB literal 0 HcmV?d00001 diff --git a/gestion_vehicule/__pycache__/forms.cpython-310.pyc b/gestion_vehicule/__pycache__/forms.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..8b3b9e0e265d218f16719d1f05e536d7c944aae9 GIT binary patch literal 2764 zcma);OK&4Z5P;|H@yysE3H#t7@BxI3h%MOVA+bUcECj?RLduH692ia9?WDszyxlV) z>+5peJBR!M|Bn2NzH(u2NGl|?5?ZQy#*Pyw&RXhnSHGv~>#ELMEl-2rUyU!>y_Tl^ ziOT%X0%a45H~>MkP$N1q5y+8q@p=mfnAx>=;Q(ld z&>=?HASQJWo5UhE(~0v`XL{(71{}y8-@fEPy=_{=|GW*$ZJ$nxnB-Y@Ist2ua?W_Y zt|4uf#`{#Rur!Sej^>Ne%)ALxr9DVuAzlP%wv9oa6+BNSV8*y8xY+6X(v6}lPH7ZL zFN(m{V0@?tQS_*cle(u7MI;|Y5jSv2cWN?eE8j?G$Y??YM;plILwa2Nkd4YhHhyDd zpB7@G@mtWP#EZNAgFK~uk#m~#lN`Ok9+kAeyY-;IUjY&w)jsJfXZJ>rrG>^ovc+p4 zT+PxQ1B;_uFWr~?4QSk%*u0I~tf0VQd=&-uo$X)MZeyDRq5tPt%TJ+eIXx7(S7YIS8A*7WO(^04hqn zoEX?kj1x2Ti3^-H$F~+wt}x?hhps98gwZl0bQJTVR$|WC5tSZ^3mP5J60QvTf%_-| z5aTv>6)dG2Nj`{^iJ=Bat9U%3JKf+?rzntCYU53L;_JBP>nIQG0$l6bYoj>R9I>fkB_g~aW^TdL%;{gu-c;)Q; za~L$FJH3F?89*2mRNhdYkLYkn2L&5W5o!LKPOCvRqQ(U~>T0`MA}T0PS$2^gj3HTZ zz&r50(#gtnkMgd?-$%8T=1fEov<4K+EL&=`y|REX#f0=h9kNU*5Xi2?jK2qKU53_j zmOg@60<+1CCBGucGLffBdjDQW6>g51g)6F1yOyfOA7;y^s_vTM4@t=Y-5m#X5TICgh5i57MSE12w@52nu23`^z%JI`B9Y` z&qpx+3D`stIQB8)YzUeF<{aNFU01PK4Y`Bk?xMhO&p$))If^ep>~z~#GAQetHgoD_ zJjy19x+--#yXpwi#cUdL8ZU?SN7!F{2x11SSHapgrvY#t+qUWbeI2+M&%TFJfs5Ks z*Hal)YSlZyA%}6cpVw)B8=q-Ns>-1%epWXRr(PDZrF*Y>ZhVC=J%Op)(gGvU*UYum Jwbh&N{txZuiW2|; literal 0 HcmV?d00001 diff --git a/gestion_vehicule/__pycache__/forms.cpython-313.pyc b/gestion_vehicule/__pycache__/forms.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..a171809058e9f8708f65c8fda201521aacc2abc4 GIT binary patch literal 4055 zcmcInO>7fK6kglA>wh~T#0d!`4sAiM8WTjRN`XKNg(Q%GvcSpGYGY5#mi2C!-3>n% zZWU551qlUmN!3$xP(cYO!7G7*APr^(C8UT~LIWZdvqGzI zSWu)kL6HmMFh8+&i1&Rmj?+40%w+j`M8h@D>uz>Zvi$rY4 zXcuu-8=|i)e+J4kp&-xzTw72H(2x?OB6lVA$)h?k zN;butWYHVszSD1xxeg28(@SOI*sNJqZ3p};s_2P6;yT2J)0)7389o9#f8ndbO`A}= z(09FXk=S<}Ypej?7Yqxdt>1M?LAiXjQ1&3Hj{C7MaCqg%9xxGak>V}l$L;~~z3@8n z>6?bkMEXhku{7V<{aAjJIP~0|dNlcHzNO=*)LiD+QYe^BEr#T#*biaa37cpa3iNDf zI!rOPv>8PPMGJ~n6x^xG^ha)FAS1_5q}C*Fy1DYhbj@NDtv1{D4uR_t4c zs*9wenI*D-Ub-hi>`V#*?B*Nbdpm-luQ--}2CAU9y5^I(j4sL7?aM-8V>+7D5UMYIi1=bj;f zC?)}xya?~P0q@~VqKELoR&e7uJPJ>7zkL%#4fU@Yj#L|tAnwls?%T6d=O)j+JUY`m zcYL7Qer0~sLR;snw(j5Cy63a`xi9;wnSP)~dul1XB{k?_bf^ycALAMd#NI0O&(%X8 zE#4dSV;3}P66YI>mKLxCxW_@%L*5|SA~!>jkAP{mbaeZA5P=hL_$9r*K7Am#OUf#k zx21%nL~DTGi;WV?i%@&wP38A*EHogzLW36XjcuvxRJRG>XvC$O=`8fY z;SW#L(`{qhMY3bK38@Dp^fqp6z~XQUj^$zKAwNKU*|mCXOQ!Wz3X@vhfEpw!(Ov48 zq{Q|>+W%^UHKT5DZ~UsN#PboFQW7+c-8^gB7&njpS73jQ{vwt&7B{Vm*Qi-0OJPY< zS3|}mLx--Li4e{Ez(n1!D#W4Ki^i=HXx+xWK6GQfq=*pC^oMb5)w*qBKsuqlu$+r< z&U+^PXg7d@yLA<{K@>wMcsrJB*qQ6K1h)#$t$5F(SXjOGR93h%EP@@YMv1mdQn&=J zpm+AKAl8zCS7vKTVgKf&u>ZiswWrsR=yEl44(Q*ENx`H4x{3^0!k9E*;q2V;{%Xg- zd~@4``jjUVKS5-0AFTSP`K#+r+mKAWcl1v7zHFJv&-L_I+Xt4q8uy%EF5tzZz!0wH zm$UE04$Lngy!?U|L%A65ikaa3L6A$|X=d5-{|^k}A41F#UT@611fIP38#eY3EON&C zPtr?o!NHIZ1RD{s7zzXeuZ0tT3H$#LT36&$Aol!|sbepWtq7p59L9O`ROgFMe||6! b`>}bV^9jsBUFq$D`OOLSiTYLmm3#g#tlV}M literal 0 HcmV?d00001 diff --git a/gestion_vehicule/__pycache__/models.cpython-310.pyc b/gestion_vehicule/__pycache__/models.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..334a79fe3e21f213327d65e3b67ed077e6d8db35 GIT binary patch literal 3872 zcmbW4&u`qu6~{>~cey{fKeUpqx@ZcbZtHAYOGSSIO3*r%EyIYS8j+gA_CQcOvl4AC zxfzmzP4t$aH(!b#3b+P(j4u5r^k2-ir~CoEw5i?in<1suDguHoz~RiBADnsbecqc* zy4|*c-=CfL!p{bV@lR?j{%kbv;Yp8CFk@^mlUb2Dv&NQ5^;%S$*<;%@9vRGL_0J7f z=hoBuXSHzyk_K}iaY~5;Nt3l8X_b;DByHA#q*F>-%-uIe-TcS++(!vJ`y%40$G8{W z3Fh-CoCH~z#NH84>FuBJ<8YEkeB(%zkN&8)!MKPA5RCiB^mD&e~{U$ISiQ7im94y(3FFSVy+MXnJZ0IHK|IUv3^JGrpN7f=8QCaumYk zpXPjX|IzN|vi&!;**E4dq~rT(CVc+}?cPGsw2DEcg^jXvZ{*6Rue9v@vhDkr4>v;H z_5DxtAR_&vg~eDh@qIxH$<_gXp6!G@Vxmj!wz7#5$hxwCbnhog#DiE1+ZRd~L(EVI zTPRjYM*c`K&XenHw$QWw%Lb6E4GIqs=C+#mHm>H{E4^%c~IgaX#;V*OP$ zuE+Xp07%x@3L65F8w%)E*?+)iLCkn%ihL9My^a-f9yOYr=z^OAAkqT%K%8e>+HoF5 z^5#59Q+U6C*pC8~YUaom@8ApKyC`J+Fbd*l(uFGp8D|==TX58TI_0_W1H2{~mYBe^ zQ=Su!yCKi%^X%+&9*FGJRB$bH-3f#Uu{oZ93&S5^VUK6tG1gPQU(PGu`6P%!rsEbC z@&I7z&6AMFd!w3KSGd(?i~dJR7ETo~f=}~Q8lr>FD~uAFiqY?*!c0vmv+y=w8LWo4 zg}04&?UnJm34ZJU`Zb3BfBbF~gCz@kh2`DN$$h=Ezk7vECmY$)nm?1B2+D&cNO5ID zDGM^Xd>~DYY;Gt|*!Bf;QS~m9|9{78|-`$mNoXq^nsbuTiOT;>@dWVX4 zX-1b!eh|*Mf?bTLm$Qo(0es9fLaU0I*1MSLTqpl7brSVY-ppugA}MG4#w%Y&|HvE zbm$;4UW}m_(WSJ`T*QF^S}Ux}da5;~=zyrO%53=KifnHO$RyeQM6jHE^Xmfw91EEQ zeHm4**bk=*tb1FSO@Z}-N&o|Erys{rI77R|yKvBlfkxdJ{R zr@$wNUk3j*DYhnlfUcr*p>d*lo~fwAn+>_R1stCNs@+Hc)}mY8AoK-*|ha+Rt<3V zyfUUxhpuY=dioQ-RwBP1yPsnZ@8e0S(5bhrQZB$!30UKYWc-!gXp~90dh6s&B~ml3 zbOpdVg!k~Ie?qYgAP}n|iRuJxt2*5>%R47){>@@7;G@%ZTlG__Cah>4f!IdsrFvJ* z>#928*yjUA?-kZZS{||iTT#gM;2A^N*M>xSmhl~1Ydy^D+IqrIJx>@095JHI=m&#R5>!R1vjpzv^osRo3K zDRR;kp}bORMcRyXb{%**HleQG z!&h7i9ZVLc*EN_!5?%FeTkFef|7 zg&H;4q$N!@CF|=6dk?)no|G~s5$0NyxWE-Ix%QjJ8=cBZ8Kt!Ux(z|I_C{@$#$}5= z4dSC@gB|LOz8>V+G5%GB)AHZo1}^XT&!^LP9iGf19eLCyiA=TN!cBwzUkJK<%jWx- ZjGO;&C0kf= literal 0 HcmV?d00001 diff --git a/gestion_vehicule/__pycache__/models.cpython-313.pyc b/gestion_vehicule/__pycache__/models.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..df86b2a0b3d53427da8cd851d1d1a9116644bb05 GIT binary patch literal 5607 zcmbW5O>7&-6@ZsN%m06ADa)3fwJb|wT**qTII$Y5u_Y_ECCi3aiEEV2VnvSRt(RP7 zc2`M=90;^1+EeWUft^#7Q>;s&oZ@2uT@3V4kry%x6fjWq;F|=?_r5nvS`am9OWdJ3N=l3m-^Gkh9(+8UVS7`c~W&kvUuh0xI%@AmYU!fUX zj%1?NDVWPOJ-_)#BZinKqBf+gtY~UZF;%@NE)xTP)tx%*nn&_V{5d!Eg9e;H z`vV$2$u9*!BM2JZ?Q#xxJ}8BxFldCO$YG8~q$rIp$1-s{@L^*S&-~EOIsrvv;UXm~ zbaUMxMN=u7qE!@EH`f~rw&Pa{1;wPee6}ag;?ObUwj-;AF6su6i%Nmmp@Qvie6L~H6s3I zVZEX0&yyv^(#)I-`ZXV{qc=V8gW?PB1MX&1(()VQ2H?o7X=u7hOx>bI0&66#t7eBy ziem1LviT1Xfg|J;s^rYgM-=_SYS|Gu^SHWyPu5+w*C5)Gf%6gV3sV!>4-7($?ByHT zX=2S%;HCRavZY77d0>jUtkz42HGch|Lvtxn&Az22i;JQ$c$nwXQqTzwTTU?fxRBD)- zS|mjs8eq)4o|9#YJ8B0P$fxFvO0+!1(d-aARn}nh>| z2A|2viU|(1Xqm(S>xV!_d$2(NrM_l?UTNHb;?LX<-jS#2zFK;)njWkRgY_<9hxhdO z%Gb98T(qkeIa-YztqZSjot@e7xTC)ErEMRVI#f#zRFeaB;aBxU_YUt)rOQ`e1l)Ya z84SnScSi%zfX{OiPVJ}P(d+?t6YuUh54)Eg?{+o>H#Y4I*;+zBkHky9b3Bb4#DyR2 z>t}tV&=)U3+XFlZNWpV18b44TV)6vY``bFhEA$UDc?#r%9pyk6SV0Wd-hJR0aVa4s zfk}dt0w$%UF50sk&2-!GX;M&%dD3+9XNO@3>ogPxp$YFM>wiSdY%CCjim8Ux`zB%)h0Bo?6pf!cKt z6eTxE+@RF<#2^fT#M{;kuORV)1aDH?6XVVV0J8jxw?XjBAUj%0v^j%Va*HDt&O_W> z6H8v)pN!XbuiUl68XN(fCvJb^g>5+mBG^wNv#q8n=;|QZK@Fo)PunO>u8yPfBoxTi z{j>HYN~(V=d17t+k+(MdPG$I=t)X-Eq;N0)K)KTm8y|l6(YGHx8K}gsmoL}5dTU(+ z)vkehAYM-$dT{#w>3TF-kEQCu$WGYT?JLi1$GBuqEpfb>IR5`iW1y7um9KyjSW5L* zVdKXxR8kkqvtX{R0n8*%R+A^U&RnY`=gU{?*x&?#@yGcm-4Gp8zVcOw4lTBxyje-j zmuFvidA@O4xVp}v;p)!}4G439V29KVf`j)J!J$(xo`nYt4q>p1N7MEIp#2a&Fo*|Ic`5Ez|V54Rn1Fi=L+EwBL!|Cf-AkycXXn%=JCS$qo zehL$Yb#IOLxe&K^|dp1Z8J=l*wZU&LhU;h)@x> zrtRtHvPlVL9k3`RAV=GbPsh>c_T(eg@8f`CP ziH?AoQt!N8K+I{1$UevP;s|`3uBtgwN-li10vV}=pmm0~{g({*A0S6;-}_2QS2f71 z{iNBn+-P#X-Tk>cI#@Ameoi$hDfQf->Zc-0Wbs`bh7aoZ=Vvl@xP^jt`1&Fa&$8Zm zzzst+!h0X_(8(C_7NGLWh<9)nd&UPW^g1j|wC%rGiU1HL{BG5Y6JjX{Z@8C$Mh`=y z9mX82v6HqpkNeyals#>ho3ylGMaElDlsUjb{I!SXSD$?O$wPJR^Ns1+_;h7_dh5)k zZO%3066!+lgWLCS-<#d`xT43mJ)U6br&H7p;=G*%@HPzRtPG_)@ z*YMPA?+Tov9lpC4@a(X@cVrHmSyIT@JdKtyvF?~W&Y=Jc^lD=r3S{KW({QpDK2i-I zd6ce%$I8r1#Ye_8$8=YRct zmxJo=;A^hry`=}*eQlS6>h84bxNFLFFa4nJe%~&K_1ziQ5m(63dBH)IInVz9dMz6; literal 0 HcmV?d00001 diff --git a/gestion_vehicule/__pycache__/tests.cpython-313.pyc b/gestion_vehicule/__pycache__/tests.cpython-313.pyc new file mode 100644 index 0000000000000000000000000000000000000000..67ef3114a3e28630f6a4c590d79c8333b5c3d17e GIT binary patch literal 208 zcmey&%ge<81n-vL&aem4k3k$5V1hC}3ji5Y8G;#t8NC_27>gJc7}A+EnO}mWH5qSl zgrpXiI42gT`e`!V;!ep*%uCPLD*=iXF#{E>WcUnHcgw-qDkiizwWv78BOt~lwK%&Z zzaXZhC_g4AKRvU!B(tzIH73~ICng=JF*83ezAQB(Gr2S;H3no-v0g#tEe@O9{1l*w aT@eS+Kt>=g1~EP`Gcq#XV^An!19AY(r#Gnp literal 0 HcmV?d00001 diff --git a/gestion_vehicule/__pycache__/urls.cpython-310.pyc b/gestion_vehicule/__pycache__/urls.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..22da592e33dec79d5a0fc1edd5a9a06d91e95fc6 GIT binary patch literal 1843 zcmc(fOK;Oa5P)sRc|V%I5}>7|MTk}?wM50GR1xCROT~eTOD>k{*`{0h5q6yb`ycor zaOcnLl~ex$5)!lVx^k1KJz~jgf4eiYv-8-v*{m7({4TwvZ>soJkbgE1-r>tDreT0F zG{6KaFhgr-nFbWV4ho??wDG?6$?O_M@&W(fT;^>s{gvL=12=9IRc*gOk7rgYwv0%U?)q`$6HLTFY~769TiT6`otc$V7l0_4{59)}cdqh0O=#-E}yL%5SeK_dK zvg<~cY5ClCwA5vOyHmb$-C3FEjOeP&&FETNFx$-qD0Aili%sf^xOKqI zm5|gK#{yEFBwyr>?36dZPvIu%1KrrIQ*+wGO zCFQg{wa1=%>O-_|qf^-h3KR%>$SsCnAj6Mcu4UP-4xHKf|7Lc%J4>BtT2X=DyScB( z-374Wfd8%~&dI~9qWrEPg(@h6vX3*5vNYRLP!8oE=N{#09{d6==-G~f=JfpYE4)Bz z(L7Rja}lusL^)NshZY1;1fs&@sYOLWlz_OJD%?XQL0kc1na5L$G(nVssHO_{P+1U* zK&7h-RvA4_y;P6^Is(rxw)&u>wRVRk(*f z6~uKQ)_6R%s4j>G5I0kWduUY$1u; z%@kH3wuOHT6Kr#c{UvNud`Mi6V%j@$h&QHFK?@H}Nb$7+P`Jm3W!E#kvB$?O85>-$ zy&?lB+UuLt#$IS%j;U#Tel-zXhk69}_>1`PuAWH-d=cCG#P;^MY7pzdFP|p-Tk_gR zl(^As@icLI-x*UEN6GaIV81iH${Dj)rWt=DiA=r8jNIyM(%+C56*Ko8YR#%JoAkGn z%6y}G#D3+_Vbmq@09ASL6Zs+o(r`;NxHw??^8wM*`-<$TKvo)pzm*(Kw z(E0FDfCp3I#u?%DplUdj?}(Ayk<-DX=~;Y7_AZHy>_N-P1+#7n3vFOEa?cb07GgamYg^=PTV=-Cu%p)Hsy>jBB41^n}K#i7VexkM=Zpv zIyL$3d2?(;f_U>>p?R!Eo46kdI}>#$&~D3<-;;zdBjLk$*=L!>>@Ou6{^@@NQ*OcA literal 0 HcmV?d00001 diff --git a/gestion_vehicule/__pycache__/views.cpython-310.pyc b/gestion_vehicule/__pycache__/views.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..914441cb64077fc3e50d36ad3240a6a638f8d530 GIT binary patch literal 16096 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

dsdTfzqwr3EQ6`}YfZ|2 zoV}Wqx8hI=`|sV@mE6)|)FQRf{>d*Uu%~8|X+C*5mCf-K=f~QsI{qVB18)*fkH;;^7oXKLvE*?L7@n|ypgIs3$Vvf&Tq?3R{iKV+3 zpEz}~az-v*r2`yWeowNox#1g8BkjoS0=yOOiwM^{Aod*mwCCVz&!K{~^Lal>yQb*$6`kEL zhNg-w{l#tL>key`Ys2C6*w;9x&Ax$_xUz#v!(s>ZQv^QZX1Hm}QsLsJ(YH7*ah~HY zXvcTj@OYxUb}UPkAlBfB?o#SXn`TT#$F)zXAc6Tuj#nJs2zNm{zHzg9XuG(}792_+ z&aiG*MDpoKI+MSeOyo<1Gcun@XXz|t-^=EnK3t*$^_O!rrxp6l4i@`Jfqq=Y_9D9R zRmZV3f@~zQ%s+jYW%VrfmJZocGM$Uyd~1gmLzAp$&&1FDGE})mN7=@liaJ5(lesII zd3MtH02YF8fhXCk(p+vHVfvBIhRN89Yb$2L3BtO^$gzu9L>n{k*t6-oG<_HK@w zF)wPzZpJ)qP^a2D4iGIebJMkIsPuO_R0^x1XljiTZJ>Mh4xj2Ltk4fqVO5F z0w~({nb6mEH8pN0a2eAbd0m=0UR9oU*%fu?Et|+eQl7%(TVBrKYDh@oWN`@X=42hlR z@kc;(bD5>3R1P6?YF_@%^V#INJWaB~LL=IdeflUFVYor*2%x5eg2`-FaxB3Iezoi0^BIgaChR)V*QjD?%U@X)8>p~sGY>iI{W)$sls zo}xP}x+8)+BDy;ScSkYUCI-8NVAsQAgkfOh zcf;cJyMQ37Tx$W&HJV(?`?_O^TZvW% zx$j%D<{>U?4syqvIWBFPu^4g+ixJh2+hgXl=F_0XZZ5*5t&oB=K491n1CAiCW7>8> z;|GQ%jaI`Jcd!xIwGo`a2<$WV>C$v)A;VD_=fpfzIxiP@Zc(oRC-QP5mUtDLo0H1i zIM6SeZKvAT3DfZ~dh48V8urXN9jWXCc=+ZhZhEWUzJ3i`i~v0&T3X={OIWPJP4`wr z;4|)0u?@L&v)&_6{M@gFKHl+9*Sm(#3E^0(H-7;811Ne@JFnS8FIChBf!#7bSd zvfrVM_Zq+sQMN{HzLv=#)wB#Z)qnDB1;5%{;cu>=mqgQjPMk^aRhRt|pU` zi^-I%Z<140BuOr<3t7p%l*y$Qpq^aF18*wBmAnu~73Iqu_L}6uw^oQSE~M0jWVDGV zY9QH_(b@qWp?H(*$#-#7vJ5uzBgnz&i|>ywznb z^0UbC4*qA~0Wk#D?c-V_1#9CAhxcdKe{x-PGzyMJ(a|nA+VB6U;Ak&6MnuP`;20Gh zV}fJsd3&$ezDH=^BeowD+7F8D<3js*v90Ic^}E;a{rK*Wfl@mrOn{>uF2UIfq}tI} zp8tr@eq^=%Si#x)qQ0?Ut^2~xHMHIH-Svs}Lqh$KSif7S-~EfO0{xwUs-VvPpXw)W z97nzW`VW6}^G6Tg6^AB-p^0bC<9}Q~v1a3Jfi(`f&{Vkj_R_5-G1M!BdLLdWgnA31 zeJf|a@Nwp*>5P}1Rz~IC0J$&zz_aD74w_J!FFZfS<;jmS?);&~y&Bxh%K-mHN`cV^C zAKTd8&|u#fM(D=G+921|aj*Yw|BGOw80-~-y>hK$aE}n&QwZ#RVk%aq>=uH%3xPdr z7E{f>H9ObbDK^D~rdY8ZQ#m5EkBIGKLi<=@|LN8CsUlLFhlJ*#Vq?45I3P3*6zjW- zja|j24y9DMRSa(v!rR2~un-;=!y`g?wm*^iB{KJ1z6S>uP|I|7f z-44x6O}(6{new7-=+(1dth1+{6?yW+Sa8Kr$MYouM#dRZ~lU4O=mj0F<^~(Da^h zTsatlNmY*u#fTYHBag9uqp0@da5c`HEhyd3Ayrb zmccR^Q{@t=MZlfjJk%r#y)8p3k?b;5JE;Y_O87Pv(IxJTo267b$AH$U-qbvp4O$~4 zLikS8!<2Oj9r-q|m@x9EkCch1Xp?nIgKcP+C+UJGVIq&K0Pd(-ka4%<=(WyDJ@(Li zlB$;3Uy@xyNnRyR#U}@;PU4Kf2aZ%al}jZSaka!0K^h0=XDAo$J!AkNxiN(rFi~m* z)*vpMlp2@$R5m#~m*6kuc}(VP=@Kg%tb`W~MKH#^9koj~luavYC?Z%gh#S$u0Q{})O%oVgq+e{?CA94-w)TmwBSPy) zu`Q~^bPkH0yM@l(V&}Nf37moW9YWgCGT%%1BD64Rg zPhAyJ_>7xrfn_aK+-jWX4dh5XWfHDY4OUizja~d*LtW5sENXqy_1%Ds8eIW?jlMh7 zzN1Br#Oqo#VqRL$N^|iwT6D4&tM=g{a#5R$GrNuFEiTWDi_Hw!RotzgnJvnAs0HNH z?qJS1;???caj$Vnwo2baE528xAKG#iy=-KD)>lvy<2vF#maAs;hu9IgCSz-@-7&qY z3`U^A6I{_6+~ugM41g0-=`$A(sG1{KO$75M9G%n291H>?Pwz+GW(F>}>BuE=c`&3c zx#YLW8Hp4s_x`ce{GiH|OI(sNye_AtQQ-PiH=Y<{X=(#}Vm_7mK3$(eQ!|Qz@+_G( zQ5rWi7nFrb!{uyQ%iY(Z)B-(9$27^rNm8lcZYYsQ>(TONRlcR;{RX4bT@-6-mq=eW zCHDp@n2K68`SGi&EoD@-Ij^dg$@!ZnM~((aVHyBd0Sg)Qi}B=H2>44Wz^w9VKEbZk zFxSvAC7{A0_8p;nDmgo9i}ZD5(jAmxE;Dy!bM+;`9?A%4o;EEcKoqncktFWCdYQ_D z)=^eipiCAC340shH|P@`$CG$!E__4tooGz?z=HWNJN%^OtfLZD9!3=4r_F|bnz>@501 zA6~zC{mv=D7lpPXxC=^@pzDTX4Q3LJch29tc=zI}JF4cI5`5bpzPIYzTkMYhmgAYf z<9TQF!NHFYik+iE=cw3uK51WMMUC7@}`MZ(-kNoXGX@Q2@&9|EGq=lNn#|^7Bqs8ui z)^M?B@WJB8i;wpRJ#SFn&KF9LP^P-&zJqQ-S3Ltof9L%lKDhqz^;Q2!QC2?`S_TDw z>~Ytsf43F`RmAqk)2seHFM9fKOg!^+7PsyAWbDycVed&{+bN3ad*Sqb=(*|nx%YE- zuuwa&>K-gu2W4QVK{HG}fi4E@{viV2whrNf2I-htq4|OaKa8%)Ab)P51AzR=%p+h5 zL4Ab-YqjSIzn3lrDy7eoZv4BFI8~klrL>MeR4`H<%lQt4%<@(kb-C8PmEfrMn~9F{ ziNAz7g(jT{j}(H82jha-ORz4`OLs_}&1G(X-BGINw6>an5;JD3Mmg0w0b+w{JJ7C~;&!^4i#qb}V`9o}43n^VAFZ#LO$s1oPGmF2S6MWv zT`Em1;Rjl8*{F%{LGYKYm1lcY)^QBV?Ep6%LAIz%rZ>E7=_J+bE8td_}#2 zyAzq|3<~Ce5IbHNjJN*71{X}RC1C|H;(|cEDdqVa0 zmGL63Ry3Q)#x}7r_Gx46;SWE#{^+!teA%}k-w|p z-*MwmG2HU=<3&&PhvPTLe+~ixzPIxi4TAe*!FqBt=cDt<&V2*{oO|?5cHmVeGJ-GD zbz1U6$e`mkv_7Dcx-kR1RM=l}m&etF=AYd^5n+RJ4$O|y(bXb13roxIW5@rW01Rxc(Ij-Rm9?L&hn%Kb zDqP&6GV(lXU+%nMRWlfB51ndi>F+ejY86gbi>ALSWif&oM(iGp9l&75JY#_koh5CZ zvBI*;rdoC#{{xKIHe;KnyNC*hSOe`OVhIvfIK*n!bfqN38eExuoxFos5ac(yUb7iq zui1>Q*NiT?raMagR6|DBWbBIYFIFqD@CwJQ?i{fySR_7GY^Ch5E2Ik>=4R}1XS_;h zD`kUSlqmNKdAcO@B->P=M$>MoUZ%<9$3 zxpLhe>uI@;>r_(iKkTmP9x9QGbo?6J;OWyH2I%dZn=2X2CnI)bT?0dQyh#K&Bibcd zsh5&zkU=#(3iB)YNuzTxS|SUf+4qtO9+ogHyaXeuD?DA+MXMw$#Yt{5iy=J;Y?vf( z?!9H*of{q|rm)nK72SGQs;1I(6PL^65{r`i2dTvjG_yR6)FpT364a$vz?Z3Of*xDwx#)Q^b5z*&woiEnb zvDB8_;I+&=#gMyi!BdUe zH!@=}eOBD_|4fyXC<+~~h33Vh(2O3|i{uBCzEL|JE$a zx8UFT3jQr)T-kg^CrSK@XGbEN-;QlzVyw-f&OF+fX*0&d-^BJ&xHkWr2un@!^+pm_ z+;e1*D;udQoV$68L>()4=!|3oa(1PPWj=W|FV&UBsm(A$9LXc6DfY7;p*sq{uI2w0 z_477)#I0p@E7QYPaA?MUhbc=1`#nl=Gw{?Ns7)&)lud#DF6Cm}yOLe=cPWW6YhR@> z_P428H{Qt2D$~E2U56BQU0L)2ivD}z)|X^%-NU^$w+=PScC2D(NC*vyq1{4g_p7*d zR}>dP;MUb}Vn^qLzK{FFj$J~>u3~qO*gYn6j}dP#WkG%z z)&2!J{GW%t;P5~k?Q89v&A-NBOi;3c!@D0sUp8E@4uAQw7m*5wKk6TEEjK6Cu7dtK z)?sT7&lKFh$E+# zYB%bsjXJqSnw`>gDtsd@X4FGXfnMr0_I>pSD zUL8faGj3hHTh%8(NspITvb&&hq8XEFCJTkVCqIVa>J|2|nJ72epvSf{swVvSWiZM_W_s{L`OAe&R0R`**Qp2wFtDp&_6TZ4-?m2f>s~SFuK$!@ zN-(}+poi6)jTXvx0!g$j*kB}I>K2Q!Ny$9CU8*jdb;zBinN!*5KR|h&Zj{-zA1)Rj zQH9R=I^@t zJchQuok^v6YD>PVyi6f0d34nnwabDiDVlYh%`MLcyZw|La!vDDqE)o1G|^Lk)uAiF z|6^qQU&PG*B?1sVcW4$3_^F3tsO9$Jt;PEXh0ur?+9!neJ?UHx9k}VfVSC=zEw&8{ zZNp;QUZHKT*mgo_J5g+Gxz~5M@BXpJwS~^ztBreJwD&z|{yNNuJp4)vg)(-TQUWW zn~YSVAoS)Ep=TzcP-q%i7a-PK*;g0?T4QFwbd7A!*i=H>#kGG`&kdM@gG+#OM7Uvy zgl*i^-~zYb(#9>AqPG0^Fj>>Ee9y!DT~*hm(lUL6t_PT3f3L!5@?Qq*FFWKqiu{_? zc$3xD*VDDZXyes$z<|4ahpVXk)NAFZkBCw+@c#Q)SX_A$k--~3r%InByG)vJ4Qd3N znL6tel;JgUC3%i!lG&+D?ijtAlV7AMWP&O$kqQ1WJ|&e_%%|{+OO+&|Ng)fR%evBH z^G{e;K_;kUAQN3&Fd_!Jp^&;iw;JdtRn(fP4LTJAQ3TT6yfhPif{p+vNHl)M)neh zZ-W#I3teqcu~fR(uFcTSLNOtymrfR4J4V+kG{y>N*lYO*Y^-nXTqHWlT$$~KaX*;3 z^^A3~N-bk-7ZR7jslLA7k@=OX|UwVx{>gJ&H)bmV^>i=~H$^gOxz6f*M# zde*8~C@ae2gu=;hAWMN)dxkyjgQY&mB{mI&To!+V-R_4Km`KG$UF9!8+-$#6iY zu~$X#>nI4Q!zBC>gk>E(BUKE@F!-~b5{{F{Wc|N~kW|H}9@Wc}B2910!E8a8HD;+$ zrR_$y9?MGlL^=5PZl37KG`qCPB2@p$(7^JtAk>7t5Dr4R`&?iJz{mgP~HEyw@}?*s2*Jz ze-Uc^;7qZ$>4Ve7&i)5uACEou3Y`a6#-CXuit%QlYcGBWhGJ@qR@cu?{^aBb__;W; z|9JfNsvAEycW5)3(P-Cy`@ffVnT?*m7@-?xlV*vV(^l9}8vb0?8(6ReRxWPEt4oAs zXQ-ZieTs)4VM*KG+O?>O`)_rZQ8FXM#YF2Fn~sth_BYNR${-&d1?Jv5wy4o(D2AKV z_|o59N)XhK&Ixn)=@UKmt9lLU*UPkTWG64b&-fMfQ-0Et-t99$MnAlvBNC*qR_9Em ze&c)&^M6jJdm*OP98~pjnW>qRwf!g60l9hC-ufwGs0I{rHZzA1GSV+VxT0Wo$+ zh#g`C^6<*>7j=y*Q$l1Dl@dFPOY2;W8C9`a_%dz-wg|!J-KB&cEdinRv!+tYgvqo=DMP`R z=gfns6A({p?Vu^9WI$;Bu(^~{-jC5zLZj)FNhw3Y^}VH}dadsWz1$f>V>?QzG1IV8 w4xyKS%`{}%z7Dm%)|Wohb|oF5^>ezER#UfAZ^lwC>M|tRcK!<@17H9HnwLwwxeWU z;WZL}Bfq2nVgye-^%o!&RB>kPO;QwutsT$z&AH7vXLfkASu^N)_-lhj4a4|Dfvb;A zV1<5hhXydf42+&hUn{V}Laz|oJ=-)k3@Cv8ivczkhQ*%?y&{-28c_ZeB4h0k*#JFxiZA zNjl$=QW@~TOM^tK5Vm#5r2~cm#Im)9p%(#8v}HYDn7V)?Pb8_@$2MUV2|PbnT-(fi zXL6np>=>`e-PO$VbCflp47!I%p{I*vXN{nPiK7_@t_U7ePDz-~=y}feDg;dvjiyCxrdRnvAf=u^&=MW5EG%=roMF* z@V*LF??cvqxB_a~_8)TrvKev~y8}*PQ%ce$D$EWssxV#@QQe$;O_i{D6jB=dY2qra zbe@E_LWe@3ULaO&OD#}Pp?kn0Ej6CWLXYKSvgVQ)(4nJw!*!pfUZ5J1 zP?<$6q4Omh)O|=j8Bxh&VUbr^U)2Y4NBx0|f?^tvng586>bmM4BzB%9Xs*~#XO z$D9Y~MHyRaB z`Y3W6e1!S+a&CwX3QP|#*Sm*QrEW|ff^Ocx&rEO<7h5krd%4#AyWWUqGMj;moD7MO!fmJvIK7%^Pz zSoN$m4fyx79sV6h%AtJZ1r=8EEQ#xC8Oye68W!PnQ$dSXqKtUNk4PK_%;8p6iao2syZTkWg)ZAdmwQ(y3gS^Oi`;v&nEl`^9s};j-}M9C zlM6EN2_Rbc#_<4gqAlX2m>*-sQ{ri_JI(;^WJ_Nofu+&5h_L`M-WKs`fS72@W->th zAN7j8w_Z~pT(7ebUF&+C3!*#UHbb8Uh(cS$h5s=_5t^Z~Fzy#W#{=a|{vwGjH_yfw zozOOGBzhCwRZA5O5mr^^2)i(w50j)^u}!Ijk!&M{B(|`s%lLt`i5`%cg|I4XY7LQO z72yrjLXsiti1etsF58&e^3L8DJz$^oEWD}pj%WG4q#>hh-^KKhB@wV*Mx?tMFp)gD z*0(^_f`SB17OJLdS1^L@vC5Wa%8F#0{_ePAj1Sjr)sD+j2uZqLn3HX1G>P%^xcOfX1p0)rY|`d-ewq*ysVa| zVS49iYm?X-x^Mf-xHnGzI(gYNH6$Cp)J0ohP1R8VoHH>}%f=#1JEz=}jj~BtWrIY$ zW`b@boio$o%=GLP5~Di1?!jm&MHZ=4d(;o3|W$d&jZ^%_%dX5 z=0b5D%4QY6zFwR~)~0Q46>V%5gQowkf{Nn&Qt|C(FTQ@yD~^wke<}ru8r^z;IWX*9 z=qYE_S%&$EdEVXoaDF!&I>0?#+Kn=?zDD#&J$hs(b?AAj|53Fuc&a{lYCHT#&bcKy z26hK6hqrf9*(Y<2+*Ca`^*ig_*l=?thgWt|2Ol4A44tkIop#R6IqUb_p-qR^c2b$g z)yD8deRyJf%2`3~@EwOQ@5Ukrx?e`3vG{K9KCjvLdOh-lYY5|YVcfZN%@wXY{EeMd zE1l6gqI`U_kr}OLMz;rkOaGc~6c*gVLZh(i7FHXD zTW;Z&Bh}o@_YVKVZdWHI90$S!A53`g@jxS;uc!0BRNeF?hyU^ozTddQEr-9olREn3 zT;tee{n(`Qh3KrS&c%DX3{wj&vo9GYx59#uy2b|S9jOnEY@c_BW*mNYC*?UfQ%|39 zE{JY=&EeMr50iCa^7o7@TyyyA`91}YFCv);2ZYsn*iZ}S2%jf=OK=2Iw2UIML;Q#;t literal 0 HcmV?d00001 diff --git a/gestion_vehicule/migrations/__pycache__/0002_alter_demandevehicule_date_heure_and_more.cpython-310.pyc b/gestion_vehicule/migrations/__pycache__/0002_alter_demandevehicule_date_heure_and_more.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..6240b389abe095f88e3ff3361a1baccce410d7e4 GIT binary patch literal 854 zcmZ8f&2G~`5Z+z?#C8+tsiG2~Tz#<%XH+$6X%9dy>B*OslNlUa{z?5)sa)Zj7vK&0 z9J~R?y>ddlK_vvU4rxkP+S&Qpo%z0*twtk{(fajun0^;p z($4GAz-P?2e$pE@^@Z|^G^yh@t;$B(MFp5Q3mtp7 zTry5*H&YVWSBV7hghvLNnFRt2w6g)2V68dW>#cV{UI!d>GcU8Vy=(|Bcxyx7NJKP( zJwh^6?uRV`g0r7sqru2)T&9aIM>RY;I(jA3GHug1S5E dcc_26qqoss>f6qnP2Z2X#$amVDwny`YX0H?SjE=yEej?hRRjiGBulg5!2(WO#QtydsC??~ZEqgA00 zJ?6?kAt?GCaZ!LQ>Fi8$00k@H#?y#rO|&qrNKV7u|Br(e{Gtg4X6@FG$YbMElG!} zslp&jJnnVpI0i}3uXL4oyjysOY+03tO;~bvcJ?N=9Lu*1n+=(yW;iA}bt|Uf6TC$l zlr%V)1yJ+E&j*&gN%H3BgStWeg20kHgqB^8V8^JDf&|=fJ_3zJxQ#_OEn=H2-mAX8 zmpzZC*z-Ywh|{obmH@O+hxmkvzIy<)r&$~aWie(7#&8Wh1mq;f+YQ6!SAjN!@uo#R z-?kj$xZG`$I)S%26^nS3&l6MTY@g6Yj*3ROA;sUfZq-O&W6GjSiB)x0$S#x3=Y~^t znP`?-JOBiJWU=`$_BjtAmXXgSQLY8`P0e;zmajN90$l9R(#WwBxx}Ja=?y`e-L}(t4mFFsjZfpYN@SmG}Vnmyw}XU4AWBs8Ts`x zo#1gh5Z<4&eLgu5QG^P~71A|63tEH%Mbbc;Ac|{N8_(o?*50kN>$4PE(&h~PHk~nFFJ!^HlNR5 zDQ!0B6kwxU!26m4y+O6a&Y_~bYOKTX^bsgzTWxAWQrDADUtWCv7fsjNO$|@SjgVR-Hu`tCu3sr-dcmY?NcGMYrK1c@5~(#pm)Div9t{q zo_03H-3k{S7N^G_ipL@ryJsv&&e#8ub0^ened*%I8It*DBdgib|p9= zA#vu?6E6U7z+=!}TJ4onZ$SZZ;lQlZ5LCfR9)I(@-^|#JbZC^8rTt#iRY4Xd zajM;35`s)SlN>?{I%pWaK(RwOQIrv7F{*54U8c(6rPb=+2_uYDZ07LtYVDuC5_4IZ zRTgaKE!bGaW4`jcrPc}UJsR^lG(8~0S{G8oPi(_R)X632_Wb<(6%oh`ln9|0#377* zA`CJR8;~myXcxUifu24Vr2XwcMi_}zSDwCZJpZFL`+;goXv(A;;ia7j;+Cz;A*=_v z%(N5dQtIk9sI?>o5eGd$w_l8{&@cjRy0jjF3_lUf65ZV{WCPe;-t3qt$fi%IW zO$)IesWg*O3~^%IA@l*eijhF7%-*zr%d~sX)K!i#RBtDVgdi?V+E4m0UgK#Y(hQsH zh#<>Uw3cU(3Zd$lHN=PL%{$lmvlLXyA3WiAA>GW9KF?IbkJ{eKfwTL|{P^JcpUj}hEX@_gYoQm0u?lk?5VjGBb q<;H0Gi|Rb8_-~Qa6dKr+(w{D&t?zD?y6^q{+T3n!?gv4o$o>sGT>g^) literal 0 HcmV?d00001 diff --git a/gestion_vehicule/migrations/__pycache__/0004_demandevehicule_motif_refus.cpython-310.pyc b/gestion_vehicule/migrations/__pycache__/0004_demandevehicule_motif_refus.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..524ca3076597cce5e6820f7ec02f60f9b0dc3b3d GIT binary patch literal 671 zcmZWnJ#X7E5apL_*>#YhL%L>Z056t-b}WiyX_h8SI%y#k-&v7CiH;~4ZP#?o56S<@ z#I;k=e^8)Ek4%FY34uHC@g4Z?9%*-W#*9|-ds5wT#(oB{y%d2X3U^2e7;wXCp7UDd zg0m9_0^|<{68TDA%UpswXVc^t)v~GZd^ihH2_DXa?OmFbATJ#3}+xdL{P8X)b zRs+^W1Ng}4O<^jC&H3GDoPSl@u3G9Am%a1s`|fFg?g09Octl!5z-7^!&QCVjURZ~^ zDQcWbnmNoFkyqi&C(8;AoKd%_j^|qYvDQ>aEz*9X^;KV(P#X~78mZ4_QK4%Enc~x9 zfKTC$Rt7lwf?vCc{n)PYzrnYx-6uAtKY4a(Ys{Q&(PYM!75Q@2V|IS>IeTtW_Vh>@ z+4cT~QCnWj*5BIjBL)=iHKmjZsqR%GxZo46{-*blKbtB)f>qI!b_N%5ir9N3pZa{* Wy`g)2`r*NkkMs$d3mSW3U;YDfgM7`Br%ZL&@+0mQ`ksHP#2%c%G`42?+$G*DS9RKv}}N*gx>(xkJK3OFGl zaptoB0RM(fNUeP3G;t{^h%0uws?)$yoagcD_x1BWPNvJtHjtz6qa1#N0DMSC(uh(x8FG?vRKJ9z4Pv2_N-y^^iqWH8eA-yN_!6+R`1U{Mp73vD@Rq3y$|nW*Jvn^@ z6BAfFaH4DH%=fz!8(3#YrPagI>iEL-@tG@QXJzE99Xe~DZ+_is9yqO^MZ>Zuy6Ko7 z8tl@%UduIv<-hXcAldLcxi`5ZvlCULv%Qxk5~Zz~hiC3tEVAdw;4=c@h{=DBeGpokqfYAxRjq@LZv7gqteOz)5N$MA*fB`R9 z$rE0RL~wS@K!Ed=frEVQd~p&7+%q=yeo-x(3KNuhrqd=@Rc!{P0xarcA?i^hbPsOO6QtkM#v4h_Z*qw|bwW5!$NSb%xB!d9cai*tVZ z`T4uF!3dkE%SV9GGOz5XubjHZn-^*IQICiaUD+0ewv(L(#+MzAlqQhW9#HROhf-d& zX<@Og2e?5RL$%1U*7OdT@!tR(Sx(xqZunNI0@JDsnX#pFo|o9Wf!g4|Jzp{Xgz7tW zoy99vVq7bYMO>&XrxjeZ7@r-V#P|0R-@KKWHuLJg&D@=dmb5l%N8|qHleVvPKvF*= z