Vous cherchez à exécuter des scripts Python en y intégrant des paramètres via la ligne de commande ? Découvrez comment interpréter ces arguments à l’aide des modules sys, getopt et argparse en Python.
En Python, pour obtenir une saisie utilisateur, vous utilisez généralement la fonction `input()`. Cependant, certaines applications nécessitent de transmettre des informations au script lors de son lancement en ligne de commande.
Ce tutoriel vous guidera à travers l’exécution d’un script Python avec des options et des arguments spécifiés directement lors de son appel. Nous allons explorer comment utiliser les modules natifs de Python pour décortiquer ces options et arguments.
C’est parti !
Comprendre `sys.argv` en Python
Si vous avez déjà programmé en C, vous savez que la ligne de commande est une méthode courante pour transmettre des données à un programme. Pour cela, la fonction `main` est structurée de manière spécifique :
#include<stdio.h> int main(int argc, char **argv){ //argc: nombre d'arguments //argv: tableau d'arguments //traitement des arguments return 0; }
Dans ce contexte, `argc` représente le nombre d’arguments et `argv` est un tableau contenant ces arguments.
Exécuter des scripts Python avec des paramètres de ligne de commande
En Python, vous lancez un script via la ligne de commande avec la syntaxe `python3 nom_du_fichier.py`. De plus, vous pouvez ajouter autant d’arguments que nécessaire après le nom du fichier :
$ python3 nom_du_fichier.py param1 param2 ... paramN
Le module `sys` facilite l’accès et le traitement de ces arguments. `sys.argv` est une liste contenant tous les arguments fournis lors du lancement du script.
Par exemple, si nous lançons `main.py` avec différents arguments :
$ python3 main.py bonjour monde python script
Nous pouvons examiner cette liste en utilisant une boucle `for` combinée à la fonction `enumerate` :
# main.py import sys for index, argument in enumerate(sys.argv): print(f"argument{index}: {argument}")
# Résultat argument0: main.py argument1: bonjour argument2: monde argument3: python argument4: script
On constate que le premier élément (à l’index 0) correspond au nom du script lui-même, et les arguments suivants commencent à l’index 1.
Ce code simple permet de récupérer et de manipuler les arguments passés en ligne de commande. Cependant, cela soulève quelques questions :
- Comment l’utilisateur sait-il quels arguments sont attendus ?
- Quelle est la signification de chaque argument ?
La réponse n’est pas évidente. Pour résoudre ce problème, les modules `getopt` ou `argparse` sont très utiles. Nous allons les explorer dans les sections suivantes.✅
Interprétation des arguments de ligne de commande avec `getopt` de Python
Voyons comment analyser les arguments en utilisant le module intégré `getopt`.
Après avoir importé `getopt` depuis le module `getopt`, vous pouvez définir les arguments à interpréter, ainsi que les options courtes et longues associées. Il est important de noter que nous devons analyser les arguments à partir de l’index 1 de `sys.argv`. Par conséquent, la portion à analyser est `sys.argv[1:]`.
Dans notre exemple, nous allons manipuler un message et un nom de fichier. Nous utiliserons les options courtes `m` et `f`, ainsi que les options longues `message` et `file`.
Mais comment indiquer qu’une option spécifique attend un argument ?
- Pour les options courtes, ajoutez un deux-points (:) après la lettre de l’option.
- Pour les options longues, ajoutez un signe égal (=) après le nom de l’option.
En appliquant ces règles, voici le code de `main.py` :
# main.py import sys from getopt import getopt options, arguments_non_optionnels = getopt(sys.argv[1:], 'm:f:', ['message=', 'file=']) print(options) print(arguments_non_optionnels)
Ici, la variable `options` contient une liste de tuples, où chaque tuple représente une option et sa valeur. La variable `arguments_non_optionnels` contient tous les arguments positionnels qui n’ont pas été reconnus comme des options.
Nous pouvons fournir le message et le nom du fichier via les options courtes ou longues.
En exécutant `main.py` avec les options longues :
$ python3 main.py --message bonjour --file fichier.txt
Les options et leurs valeurs sont regroupées dans des tuples au sein de la variable `options`. Comme aucun argument positionnel n’a été fourni, `arguments_non_optionnels` est une liste vide.
# Résultat [('--message', 'bonjour'), ('--file', 'fichier.txt')] []
De la même manière, nous pouvons utiliser les options courtes :
$ python3 main.py -m bonjour -f fichier.txt
# Résultat [('-m', 'bonjour'), ('-f', 'fichier.txt')] []
⚠️ L’option courte `-m` dans cet exemple ne doit pas être confondue avec l’indicateur de ligne de commande `-m` qui permet de lancer un module en tant que programme principal lors de l’exécution d’un script Python.
Par exemple, `python3 -m unittest main.py` exécuterait les tests unitaires en considérant `main.py` comme le point d’entrée.
Nous avons mentionné que les arguments positionnels restants sont stockés dans `arguments_non_optionnels`. Voici un exemple :
$ python3 main.py -m bonjour -f fichier.txt argument_supplementaire
La liste `arguments_non_optionnels` contient l’argument `argument_supplementaire`.
# Résultat [('-m', 'bonjour'), ('-f', 'fichier.txt')] ['argument_supplementaire']
Puisque `options` est une liste de tuples, nous pouvons la parcourir pour extraire les arguments associés à chaque option.
Maintenant, que faisons-nous du nom du fichier et du message après les avoir extraits ? Nous allons ouvrir le fichier en mode écriture et y écrire le message, converti en majuscules.
# main.py import sys from getopt import getopt options, arguments_non_optionnels = getopt(sys.argv[1:], 'm:f:', ['message=', 'file=']) print(options) print(arguments_non_optionnels) for option, argument in options: if option == '-m': message = argument if option == '-f': file = argument with open(file, 'w') as f: f.write(message.upper())
Exécutons `main.py` avec les options courtes :
$ python main.py -m bonjour -f fichier_cible.txt [('-m', 'bonjour'), ('-f', 'fichier_cible.txt')] []
Après l’exécution de `main.py`, nous pouvons observer que `fichier_cible.txt` a été créé dans notre répertoire de travail. Il contient le mot ‘bonjour’ en majuscules (‘BONJOUR’).
$ ls main.py fichier_cible.txt
$ cat fichier_cible.txt BONJOUR
Comment interpréter les arguments de ligne de commande avec `argparse`
Le module `argparse`, également intégré à la bibliothèque standard de Python, fournit des outils pour interpréter les arguments de ligne de commande et pour structurer des interfaces en ligne de commande.
Pour analyser les arguments, nous importons la classe `ArgumentParser` du module `argparse`. Nous créons ensuite une instance, `analyseur_arguments` de cette classe.
from argparse import ArgumentParser analyseur_arguments = ArgumentParser()
Nous souhaitons définir deux arguments :
- `message` : la chaîne de texte à traiter.
- `file` : le nom du fichier avec lequel interagir.
Nous utilisons la méthode `add_argument()` de l’objet `analyseur_arguments` pour définir ces arguments. L’argument `help` sert à définir une description pour chaque paramètre.
analyseur_arguments.add_argument('message', help='Chaîne de texte') analyseur_arguments.add_argument('file', help='Nom du fichier')
Jusqu’à présent, nous avons initialisé `analyseur_arguments` et défini les arguments de ligne de commande. Lors de l’exécution du script, la méthode `parse_args()` d’`analyseur_arguments` extrait les valeurs des arguments.
Les résultats sont stockés dans la variable `arguments`. Les valeurs des arguments sont ensuite accessibles via la syntaxe `arguments.nom_de_l_argument`.
Après avoir récupéré les valeurs des arguments, nous allons écrire le message, en inversant la casse des lettres (avec la méthode `swapcase()`), dans le fichier.
arguments = analyseur_arguments.parse_args() message = arguments.message file = arguments.file with open(file, 'w') as f: f.write(message.swapcase())
En combinant les étapes précédentes, voici le code complet du fichier `main.py` :
# main.py from argparse import ArgumentParser analyseur_arguments = ArgumentParser() analyseur_arguments.add_argument('message', help='Chaîne de texte') analyseur_arguments.add_argument('file', help='Nom du fichier') arguments = analyseur_arguments.parse_args() print(arguments) message = arguments.message file = arguments.file with open(file, 'w') as f: f.write(message.swapcase())
Comprendre l’utilisation des arguments de ligne de commande
Pour comprendre l’usage des arguments lors de l’exécution de `main.py`, vous pouvez utiliser l’option longue `–help` :
$ python3 main.py --help usage: main.py [-h] message file positional arguments: message Chaîne de texte file Nom du fichier optional arguments: -h, --help Montrer ce message d'aide et quitter
Il n’y a pas d’arguments optionnels. `message` et `file` sont des arguments positionnels obligatoires. L’option courte `-h` est également valide :
$ python3 main.py -h usage: main.py [-h] message file positional arguments: message Chaîne de texte file Nom du fichier optional arguments: -h, --help Montrer ce message d'aide et quitter
Comme on le voit, les deux arguments sont positionnels par défaut. Si l’un de ces arguments est manquant, une erreur sera générée.
Dans l’exemple suivant, l’argument positionnel ‘Bonjour’ est fourni pour le message, mais pas le nom du fichier.
L’erreur indique que l’argument `file` est requis.
$ python3 main.py Bonjour usage: main.py [-h] message file main.py: error: les arguments suivants sont nécessaires: file
Lorsque les deux arguments positionnels sont fournis, on observe que l’espace de noms des arguments contient les valeurs correspondantes.
$ python3 main.py Bonjour fichier1.txt
# Résultat Namespace(file='fichier1.txt', message='Bonjour')
Si nous examinons le contenu du répertoire courant, on constate que le script a créé le fichier `fichier1.txt` :
$ ls fichier1.txt main.py
Le contenu du fichier `fichier1.txt` correspond à la chaîne ‘Bonjour’ dont la casse des lettres a été inversée : ‘bONJOUR’.
$ cat fichier1.txt bONJOUR
Comment rendre les arguments de ligne de commande optionnels
Pour rendre ces arguments optionnels, il suffit de les préfixer avec `–`.
Modifions `main.py` pour que `message` et `file` deviennent optionnels.
# main.py from argparse import ArgumentParser analyseur_arguments = ArgumentParser() analyseur_arguments.add_argument('--message', help='Chaîne de texte') analyseur_arguments.add_argument('--file', help='Nom du fichier')
Puisque les arguments sont optionnels, nous pouvons définir des valeurs par défaut.
if arguments.message and arguments.file: message = arguments.message file = arguments.file else: message='Python3' file='mon_fichier.txt'
Le contenu du fichier `main.py` est maintenant le suivant :
# main.py from argparse import ArgumentParser analyseur_arguments = ArgumentParser() analyseur_arguments.add_argument('--message', help='Chaîne de texte') analyseur_arguments.add_argument('--file', help='Nom du fichier') arguments = analyseur_arguments.parse_args() print(arguments) if arguments.message and arguments.file: message = arguments.message file = arguments.file else: message='Python3' file='mon_fichier.txt' with open(file, 'w') as f: f.write(message.swapcase())
Si nous consultons l’aide, nous voyons que `message` et `file` sont devenus optionnels. Il est donc possible de lancer `main.py` sans ces arguments.
$ python3 main.py --help usage: main.py [-h] [--message MESSAGE] [--file FILE] optional arguments: -h, --help Montrer ce message d'aide et quitter --message MESSAGE Chaîne de texte --file FILE Nom du fichier
$ python3 main.py
Dans l’espace de noms des arguments, `file` et `message` sont `None`.
# Résultat Namespace(file=None, message=None)
Les valeurs par défaut `mon_fichier.txt` et `Python3` sont utilisées. Le fichier `mon_fichier.txt` est présent dans le répertoire de travail :
$ ls fichier1.txt main.py mon_fichier.txt
Il contient le mot ‘Python3’ avec la casse des lettres inversée : ‘pYTHON3’.
$ cat mon_fichier.txt pYTHON3
Vous pouvez également utiliser les arguments `–message` et `–file` pour rendre la ligne de commande plus explicite.
$ python3 main.py --message Codage --file fichier2.txt
# Résultat Namespace(file='fichier2.txt', message='Codage')
`fichier2.txt` a été créé dans le répertoire de travail :
$ ls fichier1.txt fichier2.txt main.py mon_fichier.txt
Et il contient le mot ‘cODAGE’, comme prévu.
$ cat fichier2.txt cODAGE
Conclusion
Voici un résumé des points importants abordés dans ce tutoriel :
- Comme en langage C, vous pouvez accéder aux arguments de ligne de commande en Python via le tableau d’arguments `sys.argv`. `sys.argv[0]` est le nom du script Python. Nous nous intéressons donc à l’analyse de `sys.argv[1:]`.
- Pour améliorer la lisibilité et pouvoir utiliser des options, il est préférable d’utiliser les modules `getopt` ou `argparse`.
- Le module `getopt` permet d’analyser les arguments de ligne de commande à partir de l’index 1. Vous pouvez définir des options courtes et longues.
- Lorsqu’une option attend un argument, vous devez ajouter deux-points (:) après l’option courte et un signe égal (=) après l’option longue.
- Avec le module `argparse`, vous pouvez créer un objet `ArgumentParser` et utiliser la méthode `add_argument()` pour ajouter un argument positionnel obligatoire. Utilisez `–` avant le nom d’un argument pour le rendre optionnel.
- Pour extraire les valeurs des arguments, appelez la méthode `parse_args()` sur l’objet `ArgumentParser`.
Maintenant, vous pouvez approfondir vos connaissances sur le hachage sécurisé en Python.