Python Best Practices
Installation de son environnement
Section titled “Installation de son environnement”Aujourd’hui il est conseillé d’utiliser Python 3.13 ou supérieur ! Python 3.9 est obsolète depuis octobre 2025.
Vous pouvez suivre le statut des versions de Python sur le guide officiel : devguide.python.org/versions.
Vous pouvez installer Python via:
- Le site officiel : python.org/downloads
- Le gestionnaire de paquets de votre système (ex:
apt,brew,choco, etc.) - Un gestionnaire de versions comme
pyenv: github.com/pyenv/pyenv
Démarrage naïf d’un projet
Section titled “Démarrage naïf d’un projet”La manière naïve de démarrer un projet Python est de créer un dossier, avec deux fichiers :
main.py (le code source) et requirements.txt (la liste des dépendances).
C’est une approche correcte pour la création de scripts simples et des expérimentations rapides. Cependant, pour des projets plus complexes ou visant la production, il est recommandé d’utiliser des outils de gestion de projet et de packages comme uv ou Poetry.
Outils de gestion de projet et dépendances
Section titled “Outils de gestion de projet et dépendances”-
uv (Installing uv) :
Terminal window curl -LsSf https://astral.sh/uv/install.sh | shsource $HOME/.local/bin/envInitialisation d’un projet avec
uv init(crée une structure de projet de base dans le dossier courant).Plus d’informations sur
uv init: uv - Creating projects. -
Poetry (Poetry - Installation) :
Terminal window curl -sSL https://install.python-poetry.org | python3 -Initialisation d’un projet avec
poetry init(interactif et ne créé que le fichierpyproject.toml), oupoetry new .(créé une structure de projet de base dans le dossier courant).
Toutes ces commandes visent notamment à créer pyproject.toml, le fichier de configuration
standard pour les projets Python modernes. Ce fichier définit votre projet, ses dépendances et les
configurations des outils qui l’accompagnent.
Installation de dépendances
Section titled “Installation de dépendances”Si vous souhaitez importer vos dépendances depuis un ancien fichier requirements.txt :
uv add -r requirements.txtSinon, pour installer une dépendance directement, par exemple pandas :
uv add pandasuv va automatiquement identifier la dernière version stable de pandas et l’ajouter dans le
fichier pyproject.toml de votre projet.
Syntaxe des versions de dépendances
Section titled “Syntaxe des versions de dépendances”Le standard PEP 440 définit des syntaxes pour préciser les versions des dépendances que vous souhaitez installer.
Ces syntaxes standards sont utilisables dans le fichier pyproject.toml comme dans le fichier
requirements.txt.
Les syntaxes de base sont :
==: C’est la contrainte la plus stricte, utilisée par l’exportpip freeze.>=: Version minimale, utilisée par défaut paruv add <package>.
Pour garantir la stabilité de votre projet, il est recommandé d’utiliser des contraintes de version
plus strictes que >=. Pour bénéficier des mises à jour de sécurité tout en évitant les
changements de comportement majeurs, vous pouvez utiliser la clause ~= (compatible release
clause). Par exemple :
pandas~=2.1.2est équivalent àpandas>=2.1.2,==2.1.*oupandas>=2.1.2,<2.2.0, ce qui inclut toutes les versions2.1.xà partir de la2.1.2, mais exclut la2.2.0et les suivantes.pandas~=2.1est équivalent àpandas>=2.1,==2.*oupandas>=2.1,<3.0, ce qui inclut toutes les versions2.xà partir de la2.1, mais exclut la3.0.0et les suivantes.
Ces règles fonctionne bien avec les paquets respectant le versionnage sémantique (SemVer), où les versions majeures indiquent des changements de comportement potentiellement non rétrocompatibles.
Attention aux paquets ne respectant pas ce versionnage, ou adoptant des version de style “bêta”
comme 0.x.y, où les changements mineurs peuvent introduire des changements de comportement. De
manière générale, le premier chiffre non nul doit être considéré comme le composant majeur de la
version et doit donc être fixé par une contrainte stricte (par exemple ~=0.9.3).
Niveau avancé de la gestion des dépendances
Section titled “Niveau avancé de la gestion des dépendances”Il est probable que vous ayez besoin d’outils de développement qui ne sont pas des dépendances nécessaires à l’exécution de votre application. Les gestionnaires de packages modernes permettent de définir des dépendances de développement distinctes des dépendances de production.
Pour installer une dépendance de développement, par exemple l’outil pytest :
uv add --dev pytestPour installer l’ensemble des dépendances de votre projet, ce qui inclut à la fois les dépendances de production et de développement :
uv syncCette commande s’accompagne de la création d’un fichier uv.lock, dit “lockfile”, qui contient
la liste de toutes les dépendances de votre projet, avec leurs versions exactes. Ce fichier est une
source de vérité de dépendances testées et fonctionnelles pour votre application, garantissant
que votre projet soit reproductible et que des versions fonctionnelles des dépendances soient
utilisées à chaque installation.
En production, préferez installer uniquement les dépendances de production avec les versions
exactes listées dans le fichier uv.lock :
uv sync --no-dev --frozenLa commande uv sync s’accompagne également de la création automatique d’un dossier .venv pour
l’installation des dépendances dans un environnement virtuel isolé.
Pour executer des commandes dans le contexte de cet environnement virtuel, pas besoin d’activer
manuellement l’environnement. Utilisez plutôt uv run, par exemple :
uv run <command>Plus d’informations sur la gestion des dépendances avec uv : uv - Managing dependencies.
Plus d’informations sur uv sync et uv run :
uv - Locking and syncing et
uv - Running commands in projects.
Bonus de uv : Gestion d’environnements Python
Section titled “Bonus de uv : Gestion d’environnements Python”En bonus, uv permet aussi de gérer vos environnements Python.
Installez et gérez vos versions de Python avec uv python
:
uv python listuv python install 3.13uv python use 3.13Créez et gérez vos environnements virtuels Python avec uv venv.
De ce fait, uv peut potentiellement également remplacer des outils comme pyenv et virtualenv
pour une gestion complète des versions de Python et des environnements virtuels.
FastAPI, rapidement !
Section titled “FastAPI, rapidement !”Framework d’API bien connu en Data Science : FastAPI. Des alternatives existent, comme Flask, Litestar, Django Ninja, ou Django REST framework.
uv add fastapi[standard]Structure suggérée pour une application API :
my_app/├── controller/ # contient les endpoints FastAPI├── src/ # contient la logique métier et votre code complexe├── test/ # contient les tests unitaires et fonctionnels (pour Pytest notamment)├── pyproject.toml├── uv.lock└── main.pyL’appellation controller est inspirée du pattern “Model-View-Controller” (MVC).
Démarrez votre application en développment avec :
PYTHONPATH=. uv run fastapi dev main.py --host 0.0.0.0 --port 8080PYTHONPATH=. permet d’ajouter le dossier courant au sys.path de Python, ce qui facilite
l’import des modules locaux du projet.
Outils de développement principaux
Section titled “Outils de développement principaux”Pytest (tests unitaire et fonctionnels)
Section titled “Pytest (tests unitaire et fonctionnels)”Premier outil de développement, incontournable : Pytest.
uv add --dev pytestL’outil détecte et exécute toutes les fonctions nommées test* dans les fichiers de votre
projet nommés test_*.py ou *_test.py.
Suivez la documentation de FastAPI pour créer des tests fonctionnels adaptés à ce framework.
Exécutez Pytest à la racine de votre projet avec :
PYTHONPATH=. uv run pytest .Pytest affichera le rapport des tests et des erreurs dans la console.
Pytest avec couverture
Section titled “Pytest avec couverture”Plugin Pytest pour mesurer la couverture de code : pytest-cov.
La couverture de code indique le pourcentage de lignes de code exécutées durant les tests. Cela permet d’identifier des parties du code non testées, notamment des blocs conditionnels.
uv add --dev pytest-covExécutez Pytest avec le plugin de couverture directement intégré :
PYTHONPATH=. uv run pytest --cov .Pytest affichera le rapport des tests avec une tableau supplémentaire indiquant la couverture de code pour chacun des fichiers de votre projet.
Pylint (qualité de code)
Section titled “Pylint (qualité de code)”Linter populaire pour analyser la qualité de votre code : Pylint.
Permet d’identifier des erreurs de style, des variables mal ou non utilisées, etc.
Si vous ne souhaitez pas utiliser d’outils plus complets comme Ruff, Pylint est un outil simple et efficace.
uv add --dev pylintExécutez Pylint à la racine de votre projet avec :
PYTHONPATH=. uv run pylint .Pylint affichera un rapport avec les erreurs et donnera une note globale de qualité à votre projet.
Isort (propreté des imports)
Section titled “Isort (propreté des imports)”Outil simple pour trier et organiser automatiquement les imports dans vos fichiers Python : Isort.
Si vous ne souhaitez pas utiliser d’outils plus complets comme Ruff, isort est efficace pour cette tâche spécifique.
uv add --dev isortExécutez isort à la racine de votre projet avec :
PYTHONPATH=. uv run isort . --check-onlyPYTHONPATH=. uv run isort . --applyBlack (formatage et style du code)
Section titled “Black (formatage et style du code)”Outil de formatage de code automatique, très populaire dans la communauté Python : Black.
Référence dans le domaine du formatage de code Python, mais équivalent aux capacités de formatage de Ruff, qui peut être suffisant et servir d’outil unique pour le linting et le formatage.
uv add --dev blackExécutez Black à la racine de votre projet avec :
PYTHONPATH=. uv run black .Ruff (qualité de code et formatage)
Section titled “Ruff (qualité de code et formatage)”Outil de linting et de formatage de code très populaire dans la communauté Python : Ruff.
Mentionné depuis 3 sections, Ruff permet de remplir les fonctions de Pylint, isort et Black, et bien plus encore, avec un seul outil rapide et efficace.
uv add --dev ruffExécutez Ruff à la racine de votre projet avec :
# LintingPYTHONPATH=. uv run ruff check . # rapport uniquementPYTHONPATH=. uv run ruff check --fix . # avec corrections automatiques
# FormatagePYTHONPATH=. uv run ruff format .Attention à correctement configurer Ruff pour correspondre à vos attentes et besoins. La
configuration peut être placée dans le fichier pyproject.toml de votre projet. Référez-vous à la
documentation officielle pour plus de détails :
Ruff - Configuration.
Par exemple pour le linting :
[tool.ruff]line-length = 100
[tool.ruff.lint]# https://docs.astral.sh/ruff/rules/# Select F for Pyflakes rules# Select E and W for Pycodestyle errors and warnings# Select I for isort rules# TODO: Include more rules as the codebase matures# (e.g. N (naming), C90 (complexity), S (security), and eventually ALL)select = ["F", "E", "W", "I"]# Ignore W191 to allow tab indentationignore = ["W191"]# Allow auto-fix of all fixable issuesfixable = ["ALL"]unfixable = []# Allow unused variables when underscore-prefixed.dummy-variable-rgx = "^(_+|(_+[a-zA-Z0-9_]*[a-zA-Z0-9]+?))$"
[tool.ruff.lint.isort]known-first-party = ["app"]# known-third-party = ["package"]- Important de sélectionner le jeu de règles
Ipour que Ruff joue le rôle d’isort. - Liste des règles : docs.astral.sh/ruff/rules.
Par exemple pour le formatage :
[tool.ruff]line-length = 100
[tool.ruff.format]quote-style = "single"indent-style = "tab"skip-magic-trailing-comma = falseline-ending = "lf"MyPy (vérification de types)
Section titled “MyPy (vérification de types)”Outil de vérification statique de types pour Python : MyPy.
Petite pépite pour améliorer la robustesse de votre code en garantissant la conformité des types et des signatures de fonctions dans leur usage. Permet de compenser les faiblesses d’un langage faiblement et dynamiquement typé comme Python, qui entraîne facilement des erreurs au runtime.
uv add --dev mypyPYTHONPATH=. uv run mypy --explicit-package-bases .Pre-commit, pour automatiser l’exécution des outils
Section titled “Pre-commit, pour automatiser l’exécution des outils”Une fois installés en dépendances de développement, vous pouvez automatiser l’exécution de ces outils via des scripts. Notamment en CI/CD, ou localement avec Pre-commit.
uv add --dev pre-commitCréez un fichier .pre-commit-config.yaml à la racine de votre projet pour configurer les étapes à
exécuter avant vos commits Git. Par exemple :
repos:
- repo: local hooks: # Run the ruff linter. - id: ruff-check name: ruff check (local) entry: ruff check --fix language: system types_or: [ python, pyi ] # Run the ruff formatter. - id: ruff-format name: ruff format (local) entry: ruff format language: system types_or: [ python, pyi ]Pre-commit permet aussi l’usage de scripts communautaires préconfigurés, par exemple ceux-ci : github.com/pre-commit/pre-commit-hooks.
Exécutez Pre-commit manuellement à la racine de votre projet avec :
uv run pre-commit run --all-filesOu intégrez-le dans votre workflow Git en installant le hook Git avec :
uv run pre-commit installAutres outils à explorer
Section titled “Autres outils à explorer”Pour la qualité du code
Section titled “Pour la qualité du code”-
Radon calcule des métriques de complexité cyclomatique, et des indices de maintenabilité pour les fonctions et classes de votre code.
Terminal window uv add --dev radonPYTHONPATH=. uv run radon cc . -sPYTHONPATH=. uv run radon mi . -
Flake8 est un autre outil de linting populaire, comme Pylint et Ruff. Il permet quelques vérifications supplémentaires, mais la plupart de ses fonctionnalités sont couvertes par Ruff.
Terminal window uv add --dev flake8PYTHONPATH=. uv run flake8 . -
Pydocstyle vérifie la conformité de vos docstrings avec les conventions Python. Il permet aussi de détecter les docstrings manquantes.
Terminal window uv add --dev pydocstylePYTHONPATH=. uv run pydocstyle . -
Interrogate mesure la couverture des docstrings dans votre code pour assurer une documentation technique complète et cohérente.
Terminal window uv add --dev interrogatePYTHONPATH=. uv run interrogate -v .
Pour la robustesse du code
Section titled “Pour la robustesse du code”-
Plugin Pytest pour créer des tests basés sur des propriétés, générant automatiquement des données de test variées sur des types et échelles définies pour des tests plus robustes.
Terminal window uv add --dev hypothesisPYTHONPATH=. uv run pytest --hypothesis-show-statistics -
ty est un vérificateur de types rapide développé par les créateurs de uv et Ruff. Il est actuellement en phase bêta, mais prometteur comme alternative à MyPy et Pyright.
Terminal window uv add --dev tyPYTHONPATH=. uv run ty check . -
Pyright est un vérificateur de types rapide développé par Microsoft, souvent utilisé comme alternative à MyPy. Il est également disponible en tant qu’extension pour VS Code.
En console, l’outil est plus lourd que MyPy et a notamment une dépendance à Node.js, ce qui peut le rendre moins adapté pour une intégration CI/CD ou avec Pre-commit.
Terminal window uv add --dev pyrightPYTHONPATH=. uv run pyright .
Pour la sécurité
Section titled “Pour la sécurité”-
Pip-audit est un outil qui vérifie les dépendances Python installées pour détecter les vulnérabilités de sécurité connues.
Terminal window uv add --dev pip-auditPYTHONPATH=. uv run pip-audit -
Outil de détection de secrets (comme des clés API) dans votre code source.
Terminal window uv add --dev detect-secretsPYTHONPATH=. uv run detect-secrets scan . -
Bandit analyse votre code à la recherche de vulnérabilités de sécurité et mauvaises pratiques courantes.
Terminal window uv add --dev banditPYTHONPATH=. uv run bandit -r . -
Outil SaaS pour identifier les vulnérabilités de sécurité dans vos dépendances. (Nécessite un compte SaaS sur la plateforme de Safety.)
Terminal window uv add --dev safetyPYTHONPATH=. uv run safety scan
Pour la modernisation du code
Section titled “Pour la modernisation du code”-
Pyupgrade automatise la mise à jour de la syntaxe de votre code aux passages de versions plus récentes de Python.
Terminal window uv add --dev pyupgradePYTHONPATH=. uv run pyupgrade --py313-plus
Pour la documentation
Section titled “Pour la documentation”-
Sphinx est un générateur de documentation puissant pour les projets Python, particulièrement adapté aux bibliothèques.
Terminal window uv add --dev sphinxuv run sphinx-quickstart --quiet docs -
MkDocs est un générateur de documentation statique simple pour les projets Python, adapté aux documentations de projet et guides utilisateur.
Terminal window uv add --dev mkdocsuv run mkdocs new docs -
Docs8 est un linter pour la documentation, vérifiant le style et la cohérence des fichiers Markdown et reStructuredText.
Terminal window uv add --dev doc8PYTHONPATH=. uv run doc8 docs/
TL;DR, les références rapides
Section titled “TL;DR, les références rapides”- Statut des versions de Python : devguide.python.org/versions
- uv - Installation
- Poetry - Installation
- uv - Creating projects
- Syntaxe des versions de dépendances : PEP 440 - Version Specifiers
- SemVer - Semantic Versioning
- uv - Managing dependencies
- uv - Locking and syncing
- uv - Running commands in projects
- FastAPI
- Pytest
- pytest-cov
- Pylint
- Ruff
- MyPy
- Pre-commit