Vous venez de terminer votre analyse bio-informatique. Pour cette dernière, vous avez réalisé un script qui pour l'instant, il faut le dire, n'est pas du tout réutilisable par une tierce personne. Même vous dans 6 mois vous n'êtes pas sûr de vous souvenir de ce que vous avez fait. Pourtant, l'un des intérêts de la programmation est de pouvoir répéter des calculs de manière automatique. Par conséquent, ce serait pratique de rendre votre script un peu plus souple afin de ne pas devoir modifier son code source à chaque fois qu'un paramètre de votre analyse change. De plus, il serait bien que les biologistes qui travaillent avec vous puissent également utiliser votre script, après tout le boulot d'un bio-informaticien c'est aussi de faire l'interface entre les biologistes et les informaticiens non ?
Nous allons voir comment rendre un script facilement utilisable, en gardant un code clair, le tout en Python.
sys.argv : une fausse bonne idée
Contexte
Admettons que vous ayez un script (que nous nommerons
1 |
monScript.py |
) qui prend comme paramètres le nom d'un fichier d'entrée et le nom d'un fichier de sortie. La première idée peut être de se dire que le programme doit être appelé de la façon suivante :
1 |
monScript.py input output |
Pour cela vous pouvez utiliser la bibliothèque
1 |
sys |
de Python. Cette dernière vous fournira un tableau qui permet d'accéder aux paramètres de votre ligne de commande :
1 2 3 |
# coding : utf‑8<br> import sys<br> print "Voici les paramètres entrés : "+sys.argv[1]+" "+sys.argv[2] |
Pour ceux qui se posent la question,
1 |
sys.argv[0] |
correspond au nom de votre script.
Ça se complique
Vous pouvez tout à fait faire fonctionner votre script ainsi, seulement il y aura des tests à effectuer, notamment pour savoir si le fichier d'entrée existe. Certes un
1 |
if |
au début de votre code pourrait faire l'affaire.
Cependant, imaginons maintenant que votre script qui réalise plusieurs étapes, puisse afficher le temps de calcul de chaque traitement, ou pas, selon les désirs de l'utilisateur. Pour cela il faudrait rajouter une option, par exemple "-t" comme Time. Votre script se base sur un logiciel dont il connaît la localisation mais que faire si un jour il est installé dans un autre répertoire ? Ça peut être le cas si plusieurs versions d'un même logiciel coexistent sur une machine. Il faudrait que votre script par défaut fasse appel au répertoire d'installation classique du logiciel (ex : /usr/bin/soft) mais, qu'il soit également possible de spécifier un autre chemin, dans le cas où on voudrait tester une nouvelle version par exemple. Une option "–path" serait la bienvenue pour cela. Enfin, comme dans tout logiciel utilisable en ligne de commande, on aimerait que l'option "-h" ou "–help" affiche l'aide.
Pour réaliser tout ceci vous pouvez vous engouffrer dans des
1 |
if |
sans fin en utilisant la bibliothèque
1 |
sys |
mais vous voyez bien que cela devient vite compliqué.
args parse : gérer plus finement les options en ligne de commande
Les différentes options décrites précédemment peuvent simplement être implémentées de la manière suivante :
1 2 3 4 5 6 7 8 9 |
# coding : utf‑8<br> import argparse<br> softPath="/usr/bin/soft"<br> parser = argparse.ArgumentParser()<br> parser.add_argument("input", help="Input File",type=argparse.FileType('r'))<br> parser.add_argument("output", help="Output File",type=argparse.FileType('w'))<br> parser.add_argument("-t", help="Print time",action='store_true')<br> parser.add_argument("–path", help="Path to software",default=softPath)<br> parser.parse_args() |
Et voilà !
Deux choses intéressantes sont à noter :
- Vous avez séparé la gestion des options de l’exécution du programme. Plus besoin d'ajouter une tonne de
if au début de votre script. Tout ceci est fait automatiquement, vous avez juste à vous concentrer sur votre programme en lui-même. Si vous désirez rajouter une option vous n'avez qu'une ligne à ajouter, vous n'avez pas besoin de "tout casser" dans votre code. - L'aide est réalisée automatiquement. Vous pouvez l'afficher avec l'option "-h" ou "–help", cf. ci-dessous.
![Exemple d'aide crée par argsparse](https://i0.wp.com/bioinfo-fr.net/wp-content/uploads/2016/05/blogBioInfo.jpg?resize=409%2C146&ssl=1)
La bibliothèque
1 |
argsparse |
permet de faire de nombreuses choses, je vous invite à lire la doc pour obtenir plus d'informations.
Gooey : l'ajout d'interface graphique
Notre script peut maintenant afficher une aide conviviale, ce qui est bien sympathique pour les utilisateurs sensibilisés aux lignes de commande. Mais que faire pour les autres ?
Bonne nouvelle, la bibliothèque Gooey permet de réaliser une interface graphique en ajoutant 4 lignes à notre code précédent !
- Mettez votre programme dans une fonction, vous pouvez choisir
main par exemple - Ajoutez
@Gooey au dessus de votre fonction - Importez la bibliothèque :
from gooey import Gooey - N'oubliez pas d’appeler votre fonction
main dans votre code :)
Voilà ce que ça donne pour notre exemple :
1 2 3 |
# coding : utf‑8<br> import argparse<br> from gooey import Gooey |
@Gooey
def main():
softPath="/usr/bin/soft"
parser = argparse.ArgumentParser()
parser.add_argument("input", help="Input File",type=argparse.FileType('r'))
parser.add_argument("output", help="Output File",type=argparse.FileType('w'))
parser.add_argument("-t", help="Print time",action='store_true')
parser.add_argument("–path", help="Path to software",default=softPath)
parser.parse_args()
main()
Et voici la fenêtre obtenue :
![Exemple de fenêtre créée par Gooey](https://i0.wp.com/bioinfo-fr.net/wp-content/uploads/2016/05/gooey.jpg?resize=602%2C545&ssl=1)
Bien entendu, la fenêtre est "simple" mais par rapport au peu de lignes de code demandées pour la générer ça me semble être un bon compromis.
Vous savez maintenant comment faire pour ajouter des options à votre script sans que ça soit l'anarchie dans votre code, puis comment ajouter une fenêtre en seulement quelques lignes de code, à vous de jouer !
Merci à Nico M., NiGoPol et Nisaea_ pour les commentaires et discussions lors de l’édition de cet article.
Laisser un commentaire