venv, pip et variables d'environnement
Isoler les paquets d'un projet dans un venv, figer leurs versions dans requirements.txt, lire une variable d'environnement avec os.environ et savoir pourquoi un secret n'a rien à faire dans le code ni dans git.
Mis à jour le
À recouper avec le cours. Cette leçon a été écrite à partir du plan du chapitre, avant relecture avec les supports. En cas de doute, le cours fait foi.
Pourquoi on voit ça
Jusqu’ici, ton outil de vérification du parc n’utilisait que ce que Python fournit de base. Dès qu’il doit appeler une API ou envoyer une alerte, il lui faut un paquet externe comme requests, et un secret : un token, une URL de webhook.
Deux questions arrivent alors. Où installer les paquets pour que l’outil marche pareil sur ta machine, sur celle d’un collègue et sur le serveur ? Et où ranger le secret pour qu’il ne se retrouve pas dans git ? Les réponses sont le venv et les variables d’environnement. C’est la base de tout projet Python en DevOps.
Un venv : une boîte de paquets par projet
Sans venv, pip install installe les paquets pour tout le système. Trois ennuis :
- deux projets peuvent avoir besoin de deux versions différentes du même paquet ;
- tu risques de casser des outils du système qui dépendent de Python ;
- tu ne sais plus quels paquets appartiennent à quel projet.
Un venv (environnement virtuel) est un dossier qui contient son propre python et son propre pip. Tout ce que tu installes va dedans, et seulement dedans. Pense à une caisse à outils par chantier, au lieu d’un seul atelier où tout se mélange.
Créer, activer, installer
python -m venv .venv
source .venv/bin/activate
pip install requests
| Commande | Ce qu’elle fait | Quand |
|---|---|---|
python -m venv .venv |
crée le dossier .venv |
une fois par projet |
source .venv/bin/activate |
active le venv dans ce terminal | à chaque nouveau terminal |
pip install requests |
installe le paquet dans le venv | quand il te faut un paquet |
deactivate |
quitte le venv | quand tu as fini |
Sous Windows, l’activation s’écrit .venv\Scripts\activate.
Quand le venv est actif, l’invite du terminal commence par (.venv). C’est ton repère : sans ce préfixe, pip install vise le système.
Créer n’est pas activer. Si tu crées le venv sans l’activer, tes commandes python et pip restent celles du système.
Le dossier .venv ne va pas dans git. Il est gros, il dépend de ta machine, et il se reconstruit en une commande. On l’ajoute au fichier .gitignore.
requirements.txt : la liste des paquets
Puisque le venv ne voyage pas, il faut faire voyager la liste de ce qu’il contient.
pip freeze > requirements.txt
pip freeze affiche chaque paquet installé avec sa version exacte. Le > du shell écrit cette sortie dans le fichier. Résultat, par exemple :
certifi==2026.1.4
requests==2.32.3
urllib3==2.3.0
Tu y trouves requests, mais aussi les paquets dont requests a lui-même besoin.
Versions épinglées
Le == épingle la version : une seule version possible, la même pour tout le monde.
| Ligne | Ce que pip installe |
|---|---|
requests==2.32.3 |
exactement la 2.32.3 |
requests>=2.0 |
la plus récente à partir de la 2.0 |
requests |
la plus récente, quelle qu’elle soit |
Sans épinglage, l’outil qui marche aujourd’hui peut casser dans six mois, quand une nouvelle version du paquet sort. Avec, l’installation est reproductible.
Réinstaller ailleurs
Sur une autre machine, ou dans un venv tout neuf :
python -m venv .venv
source .venv/bin/activate
pip install -r requirements.txt
Le -r dit à pip de lire la liste dans le fichier. Ne confonds pas les deux sens :
pip freeze > requirements.txt: du venv vers le fichier ;pip install -r requirements.txt: du fichier vers le venv.
os.environ : lire une variable d’environnement
Une variable d’environnement est une valeur que le shell transmet au programme qu’il lance. On la définit avec export :
export FLEET_ENV=prod
python fleetcheck.py
Côté Python, os.environ se lit comme un dictionnaire. Tu retrouves donc les deux écritures de la leçon sur les collections.
| Écriture | Si la variable existe | Si elle manque | À utiliser pour |
|---|---|---|---|
os.environ["X"] |
sa valeur | KeyError |
une variable obligatoire |
os.environ.get("X") |
sa valeur | None |
une variable facultative |
os.environ.get("X", "dev") |
sa valeur | "dev" |
une variable avec valeur par défaut |
Avec FLEET_ENV=prod défini et FLEET_TOKEN absent :
import os
print(os.environ["FLEET_ENV"])
print(os.environ.get("FLEET_TOKEN"))
print(os.environ.get("FLEET_REGION", "eu"))
print(os.environ["FLEET_TOKEN"])
prod
None
eu
KeyError: 'FLEET_TOKEN'
Une valeur lue dans l’environnement est toujours une chaîne. Avec export FLEET_TIMEOUT=5, os.environ["FLEET_TIMEOUT"] vaut "5", pas 5. Pour calculer, convertis avec int().
Les secrets : jamais dans le code, jamais dans git
Un secret est une valeur qui donne un accès : un token d’API, un mot de passe, une URL de webhook. Une URL de webhook est bien un secret : quiconque la connaît peut poster des messages dans ton canal d’alerte.
Pourquoi ne pas l’écrire dans le script ?
- Le code part dans git, et git n’oublie rien. Même si tu effaces la ligne au commit suivant, le secret reste lisible dans l’historique.
- Tous ceux qui ont accès au dépôt ont alors accès au secret.
- Pour changer de token, il faudrait modifier le code.
La solution : le code ne contient que le nom de la variable. La valeur reste sur la machine.
export FLEET_WEBHOOK="https://hooks.example.com/services/XXXX"
import os
url = os.environ.get("FLEET_WEBHOOK")
if url is None:
print("pas de webhook : aucune alerte envoyée")
else:
print("alerte envoyée")
Sans la variable, le code affiche :
pas de webhook : aucune alerte envoyée
Ici, le webhook est facultatif : on utilise get et on teste None. Si le secret était obligatoire, on prendrait les crochets, et le KeyError signalerait tout de suite l’oubli. Dans les deux cas, on n’affiche jamais la valeur du secret, ni avec print ni dans les logs.
À retenir
- Un venv est un dossier de paquets propre à un projet :
python -m venv .venvle crée,source .venv/bin/activatel’active. pip freeze > requirements.txtécrit la liste ;pip install -r requirements.txtla réinstalle.==épingle une version exacte : l’installation est la même partout.- On versionne
requirements.txt, jamais.venv. os.environ["X"]lèveKeyErrorsi la variable manque ;os.environ.get("X")renvoieNone. La valeur est toujours une chaîne.- Un secret (token, URL de webhook) se lit dans une variable d’environnement : jamais dans le code, jamais dans git.
Entraînement
12 questions, dont 4 à compléter. Tu réponds, on passe à la suivante. La note arrive à la fin.
Ta note
Cartes · 7
Réviser les cartes ici
Pourquoi