Spaces:
Sleeping
title: Attrition API (FastAPI)
colorFrom: purple
colorTo: indigo
sdk: docker
pinned: false
Prédiction de l’Attrition des Employés – TechNova Partners
Bienvenue dans ce projet de classification en Machine Learning dont l’objectif est d’analyser et prédire les démissions d’employés (attrition) au sein de l’ESN TechNova Partners, spécialisée dans le conseil en transformation digitale et la vente de solutions SaaS.
Ce dépôt contient l’ensemble du travail réalisé en tant que Consultant Data Scientist pour :
- comprendre les facteurs clés derrière les démissions,
- construire un modèle de prédiction de l’attrition,
- produire des insights actionnables pour les équipes RH
Table des Matières
- Contexte & objectifs
- Jeux de données
- Approche
- Structure du dépôt
- Mise en place du modèle
- API(FastAPI)
- Base de donées PostgreSQL
- Installation
- Utilisation
- Workflow Git
- Traçabilité des prédictions
- Tests & Couverture (CI)
- Déploiement(CI/CD)
- Déploiment HF Spaces (Docker)
- Livrables
- Auteur
Contexte & objectifs
Problème : anticiper les départs d’employés (attrition) et expliquer les facteurs clés.
Objectifs:
- Construire un pipeline scikit-learn (prétraitements + modèle RF)
- Exposer une **API ** (FastAPI) avec Swagger/OpenAPI.
- Tracer chaque prédiction (inputs/outputs) dans PostgreSQL
- Mettre en place CI (tests) et CD (déploiement automatique).
Jeux de données
Trois sources principales sont mises à disposition :
SIRH: poste, département, contrat, âge, ancienneté, salaire, etc.
Évaluations de performance: notes annuelles, engagement/satisfaction, historiques RH.
Sondage annuel employés: bien-être, charge, management, équilibre vie pro/perso.
Variable cible (attrition = 1/0)
Ces différentes sources sont fusionnées et préparées pour construire un dataset modélisable.
Fichier aligné pour l’inférence : data/processed/df_central_norm.csv
(contient le feature engineering attendu par le pipeline et les schémas SQL).
Approche
Préparation : encodages catégoriels, normalisation, features (
exp_moins_3_years, etc.).Modèle :
RandomForestClassifierdans un Pipeline scikit-learn.API : FastAPI + endpoints
predict_oneetpredict_proba.Traçabilité : table
ml.predictions_log(inputs/outputs/threshold).Déploiement : Docker → Hugging Face Spaces (CD GitHub Actions).
Qualité : Pytest + couverture, règles de branche et PR.
Structure du dépôt
.
├── src/
│ ├── __init__.py
│ ├── data_preparation.py. # chargement & split X/y (données traitées)
│ ├── train_model.py # entraînement + sauvegarde artefact
│ └── utils.py # utilitaires (chargement modèle, prédiction unitaire)
├── tests/
│ ├── test_data_preparation.py
│ └── test_predict.py
├── models/ # artefact modèle
├── data/
│ ├── raw/ # fichiers brutsv(privé, ignoré) – .gitkeep
│ └── processed/ # données traités (visibles)
├── db/
│ ├── attrition_local.session.sql # schémas hr_staging/hr/ml + indexes + logs
│ ├── create_db.py # création table + exemple
│ └── load_csv.py # chargement CSV → hr.employees
├── notebooks/
│ ├── 01_analyse_exploratoire.ipynb
│ ├── 02_preprocessing.ipynb
│ └── 03_modelisation.ipynb
├── .github/workflows/
│ ├── ci.yml
│ └── deploy-to-hf-space.yml
├── main.py # entraînement
├── pyproject.toml # configuration de l'environnement & dépendances
├── requirements.txt. # exporté depuis uv
├── README.md
├── .gitignore
└── uv.lock
├── Dockerfile # verrouillage précis des versions
Mise en place du modèle
Entraînement : notebooks 01_analyse_exploratoire.ipynb, 02_preprocessing.ipynb et 03_modelisation.ipynb.
Artefact modèle :
model.joblib(hébergé sur Hugging Face Hub, téléchargé à l’inférence).Chargement côté API : si
models/model.joblibest absent, l’API télécharge depuisveranoscience/attrition-model.Seuil :
THRESHOLD=0.33→pred= (proba >= 0.33)`.
API (FastAPI)
Doc Swagger :
/docsEndpoints principaux :
GET /health → statut, source du modèle (local ou hub), threshold.
POST /predict_one → prédiction unitaire (retourne proba et pred).
POST /predict_proba → prédictions batch (retourne listes probas et preds).
Exemple :
curl -s -X POST http://127.0.0.1:8000/predict_one \
-H "Content-Type: application/json" \
-d '{
"age":41, "genre":"F", "revenu_mensuel":6000, "statut_marital":"Célibataire",
"departement":"Consulting", "poste":"Consultant",
"nombre_experiences_precedentes":6, "annees_dans_le_poste_actuel":2,
"note_evaluation_precedente":3, "note_evaluation_actuelle":3,
"heure_supplementaires":0, "augementation_salaire_precedente":12,
"nombre_participation_pee":1, "nb_formations_suivies":2,
"distance_domicile_travail":5, "niveau_education":2,
"annees_depuis_la_derniere_promotion":1, "annes_sous_responsable_actuel":2,
"satisfaction_globale":3.0, "exp_moins_3_years":0,
"domaine_etude":"Infra & Cloud", "frequence_deplacement":"Occasionnel"
}'
# → {"threshold":0.33,"proba":0.1443,"pred":0}
Base de données PostgreSQL
Objectif : assurer une traçabilité complète des échanges API ↔ modèle.
- Schémas :
hr_staging : réception brute (employees_raw).
hr : table typée finale (employees) + index.
ml : table de log des inférences (predictions_log) + index.
- Scripts :
db/attrition_local.session.sql → crée schémas/tables/index.
db/load_csv.py → charge data/processed/df_central_norm.csv dans hr.employees.
db/create_db.py → exemple alternatif (table simple predictions + insertion d’une ligne).
Activation du logging DB côté API (local) :
export DATABASE_URL="postgresql+psycopg2://appuser:appuser@localhost:5432/attrition"
uvicorn src.api.server:app --reload
# Chaque appel /predict_* crée une ligne dans ml.predictions_log
Installation locale
Prérequis
Python 3.10+
git
PostgreSQL 15 local
(macOS : brew install postgresql@15)
Setup Python
uv venv && source .venv/bin/activate
uv sync
Démarrer l'API
uvicorn src.api.server:app --reload
# Swagger: http://127.0.0.1:8000/docs
Utilisation
- Lancer les notebooks
Depuis la racine du projet, avec l’environnement activé :
jupyter notebook
Puis ouvrir:
notebooks/01_analyse_exploratoire.ipynbpour l’analyse exploratoirenotebooks/02_preprocessing.ipynbpour le nettoyage & feature engineeringnotebooks/03_modelisation.ipynbpour la modélisation et SHAP
Script (entrai&nement rapide)
python main.py
Un artefact est sauvegardé dans models/model.joblib
Healthcheck
curl -s http://127.0.0.1:8000/health | jq
Batch
curl -s -X POST http://127.0.0.1:8000/predict_proba \
-H "Content-Type: application/json" \
-d '{"inputs":[{ ... les mêmes champs que /predict_one ... }]}'
Workflow Git (branches / commits / tags)
- Branche principale :
main(protégée) - Conventions de branches :
<type><-resume->- Types :
feat,fix,docs,refactor,chore,test,data - Examples :
docs/mise-a-jour-readme
- Types :
- Commits descriptifs:
feat: ...,chore: ... - Tags de version :
v0.1.0,v0.2.0, ...- Créer :
git tag -a v0.1.0 -m "v0.1.0: base" - Pousser :
git push origin v0.1.0
- Créer :
Résolution de conflits : utiliser l’outil intégré VS Code
(Accept Current/Incoming → git add . → git rebase --continue).
Traçabilité des prédictions
Activation : définir la variable d’env. DATABASE_URL avant de lancer l’API.
export DATABASE_URL="postgresql+psycopg2://appuser:appuser@localhost:5432/attrition"
uvicorn src.api.server:app --reload
À chaque appel réussi : insertion dans ml.predictions_log (date, payload, proba, classe, seuil, statut).
Requête de contrôle :
SELECT created_at, proba, pred, threshold, status
FROM ml.predictions_log
ORDER BY created_at DESC
LIMIT 5;
Tests & Couverture (CI)
Lancer localement :
uv run pytest
# avec couverture:
uv run pytest --cov=src --cov-report=term-missing
CI GitHub Actions (.github/workflows/ci.yml) :
installe l’environnement,
exécute Pytest,
calcule la couverture,
bloque la PR si la CI échoue.
Déploiement (CD) vers Hugging Face Spaces
Dockerfile à la racine.
Workflow
deploy-to-hf-space.yml:clone le repo du Space,
copie
Dockerfile,pyproject.toml,src/, db/, README.md, etc.,push vers le Space → rebuild automatique → API en ligne.
Secrets requis (GitHub → Settings → Secrets and variables → Actions) :
HF_TOKEN: token Hugging Face (scope write).HF_SPACE_SLUG: slug owner/SpaceName (ex. veranoscience/OpenClassroomsProject).
Cycle CD :
Crée une branche → commit → PR.
Merge vers
main.L’Action CD se lance et déploie sur le Space.
Déploiement HF Spaces (Docker)
- Dockerfile à la racine. Le Space utilise
sdk: docker.
Port par défaut 7860. L’API est servie par Uvicorn.
Modèle téléchargé au démarrage si absent localement.
Livrables
Le projet fournit :
Dépôt Git structuré : code source,
pyproject.toml, historique (branches/PR/tags), README.API FastAPI fonctionnelle, documentée (Swagger), déployée (Docker + HF Spaces).
Tests Pytest + rapport de couverture (via CI).
Base PostgreSQL : schémas SQL, scripts de création/chargement, logs d’inférence.
CI/CD : GitHub Actions (CI PR & CD déploiement auto).
Auteur
Projet pédagogique - Ksenia Dautel