Article de reference

Script Shell

Modification d'un script shell FreeBSD pour la configuration d'ipfirewall Un script shell est un programme informatique conçu pour être exécuté par un shell Unix , un interpréte...

Modification d'un script shell FreeBSD pour la configuration d'ipfirewall

Un script shell est un programme informatique conçu pour être exécuté par un shell Unix , un interpréteur de commandes . Les différents dialectes des scripts shell sont considérés comme des langages de commandes . Les opérations typiques effectuées par les scripts shell incluent la manipulation de fichiers, l'exécution de programmes et l'affichage de texte. Un script qui configure l'environnement, exécute le programme et effectue les opérations de nettoyage ou de journalisation nécessaires est appelé un wrapper .

Le terme est également utilisé plus généralement pour désigner le mode automatisé d'exécution d'un interpréteur de commandes du système d'exploitation. Chaque système d'exploitation utilise un nom particulier pour ces fonctions. Tous les systèmes de type Unix incluent au moins un interpréteur de commandes POSIX , généralement bash ou le mode de compatibilité zsh .

Capacités

Commentaires

Les commentaires sont ignorés par l'interpréteur de commandes. Ils commencent généralement par le symbole dièse ( ##) et se poursuivent jusqu'à la fin de la ligne.

Choix configurable du langage de script

Le shebang , ou hashbang, est un type de commentaire particulier utilisé par le système pour déterminer l'interpréteur à utiliser pour exécuter le fichier. Le shebang doit figurer en première ligne du fichier et commencer par un caractère vide #!. Dans les systèmes d'exploitation de type Unix, les caractères suivant ce #!caractère vide sont interprétés comme le chemin d'accès à un programme exécutable qui interprétera le script.

Raccourcis

Un script shell peut fournir une variante pratique d'une commande système où des paramètres d'environnement spéciaux, des options de commande ou un post-traitement s'appliquent automatiquement, mais d'une manière qui permet au nouveau script de toujours agir comme une commande Unix tout à fait normale .

Un exemple serait de créer une version de ls , la commande permettant de lister les fichiers, en lui donnant un nom de commande plus court l, qui serait normalement enregistré dans binle répertoire d'un utilisateur sous le nom , et un ensemble d'options de commande par défaut pré-fournies. /home/username/bin/l

#!/bin/sh LC_COLLATE = C ls -FCas " $@ "

Ici, la première ligne utilise un shebang pour indiquer l'interpréteur à utiliser pour exécuter le reste du script. La seconde ligne crée une liste avec des options pour les indicateurs de format de fichier, le nombre de colonnes, l'affichage de tous les fichiers (sans omission) et la taille en blocs. L' LC_COLLATE=Coption `--class` définit l'ordre de classement par défaut afin de ne pas mélanger les majuscules et les minuscules, d'éviter le mélange des fichiers cachés avec les noms de fichiers classiques (effet secondaire de l'ignorance de la ponctuation dans les noms ; les fichiers cachés ne sont généralement affichés que si une option comme `--class` -aest utilisée), et l' "$@"option `--parameters` permet de transmettre tous les paramètres fournis à l`ls` comme paramètres de `ls`, afin que toutes les options et la syntaxe habituelles de `ls` restent utilisables.

L'utilisateur pourrait alors simplement l'utiliser lpour la liste restreinte la plus couramment utilisée.

Un autre exemple de script shell pouvant servir de raccourci serait d'imprimer la liste de tous les fichiers et répertoires contenus dans un répertoire donné.

#!/bin/sh clair ls -al 

Dans ce cas, le script shell commencerait par sa ligne de démarrage habituelle : `#!/bin/sh` . Ensuite, il exécuterait la commande `clear` , qui efface tout le texte du terminal avant de passer à la ligne suivante. La ligne suivante fournit la fonction principale du script. La commande `ls -al` liste les fichiers et répertoires présents dans le répertoire depuis lequel le script est exécuté. Les attributs de la commande `ls` peuvent être modifiés selon les besoins de l'utilisateur.

Travaux par lots

Les scripts shell permettent d'exécuter automatiquement plusieurs commandes qui seraient normalement saisies manuellement dans une interface en ligne de commande, sans avoir à attendre l'intervention de l'utilisateur à chaque étape. Par exemple, dans un répertoire contenant trois fichiers de code source C, plutôt que d'exécuter manuellement les quatre commandes nécessaires à la compilation du programme final, on peut créer un script pour les shells compatibles POSIX , nommé ici buildet placé dans le même répertoire, qui les compilera automatiquement :

#!/bin/sh printf 'compilation en cours... ' cc -c foo.c cc -c bar.c cc -c qux.c cc -o monprog foo.o bar.o qux.o printf 'terminé. '

Le script permettait à l'utilisateur d'enregistrer le fichier en cours d'édition, de mettre l'éditeur en pause, puis d'exécuter la commande ./buildpour créer le programme mis à jour, le tester, et enfin revenir à l'éditeur. Cependant, depuis les années 1980 environ, ce type de script a été remplacé par des utilitaires comme make , spécialisés dans la compilation de programmes.

Généralisation

Les traitements par lots simples sont courants pour les tâches isolées, mais l'utilisation de boucles, de tests et de variables shell offre une bien plus grande flexibilité aux utilisateurs. Un script shell POSIX permettant de convertir des images JPEG en images PNG, où les noms des images sont fournis en ligne de commande (éventuellement via des caractères génériques) au lieu d'être listés individuellement dans le script, peut être créé à l'aide de ce fichier, généralement enregistré dans un fichier comme/home/username/bin/jpg2png

#!/bin/sh for jpg ; do # utiliser $jpg à la place de chaque nom de fichier donné, tour à tour png = ${ jpg %.jpg } .png # construire la version PNG du nom de fichier en remplaçant .jpg par .png printf 'conversion de "%s" ... ' " $jpg " # afficher les informations d'état à l'utilisateur exécutant le script if convert " $jpg " jpg.to.png ; then # utiliser convert (fourni par ImageMagick) pour créer le PNG dans un fichier temporaire mv jpg.to.png " $png " # si cela a fonctionné, renommer l'image PNG temporaire avec le nom correct else # ...sinon afficher une erreur et quitter le script printf > & 2 'jpg2png : erreur : échec de l'enregistrement de la sortie dans "jpg.to.png". ' exit 1 fi # fin de la construction de test "if" done # fin de la boucle "for" printf 'toutes les conversions ont réussi ' # annoncer la bonne nouvelle à l'utilisateur

La jpg2pngcommande peut ensuite être exécutée sur un répertoire entier rempli d'images JPEG en seulement/home/username/bin/jpg2png *.jpg

Programmation

De nombreux interpréteurs de commandes modernes offrent diverses fonctionnalités généralement réservées aux langages de programmation généralistes plus sophistiqués , telles que les structures de contrôle de flux, les variables, les commentaires , les tableaux, les sous-programmes , etc. Grâce à ces fonctionnalités, il est possible d'écrire des applications relativement sophistiquées sous forme de scripts shell. Cependant, ces applications restent limitées par le fait que la plupart des langages shell ne prennent que peu ou pas en charge les systèmes de typage de données, les classes, le multithreading, les calculs mathématiques complexes et d'autres fonctionnalités courantes des langages complets. De plus, ils sont généralement beaucoup plus lents que le code compilé ou les langages interprétés conçus pour optimiser les performances.

Les outils Unix standard sed et awk offrent des capacités supplémentaires pour la programmation shell ; Perl peut également être intégré dans des scripts shell, tout comme d'autres langages de script comme Tcl . Perl et Tcl sont également livrés avec des kits d'outils graphiques.

Langages shell typiques

Les langages de script couramment utilisés sur les systèmes d'exploitation UNIX, Linux et conformes à la norme POSIX comprennent :

  • Le concept original de Bourne ( sh), bien que n'étant plus couramment utilisé car protégé par les droits d'auteur d'AT&T, est désormais obsolète.
  • Coquille Almquist ( ash), variante de la coquille Bourne, sous copyright AT&T
  • Debian Almquist shell ( dash), une réplication Open Source d'ash, c'est-à-dire « ...le shell le plus rapide de l'Ouest ».
  • GNU Bash (Bourne Again SHell) ( bash), Réplication Open Source de Bourne Shell, maintenant avec plus de fonctionnalités
  • Debian BusyBox Dynamic Interface ( BusyBox Dynamic Interface), une ancienne version de BASH pour Debian 1.3 et versions antérieures, Slackware et certains Void.
  • Le shell Fish ( fish), bien que ses mainteneurs ne s'engagent pas à maintenir POSIX, notamment dans les cas où sa syntaxe est peu intuitive, est compatible avec BASH et suit les principes de BASH.

Les shells non POSIX couramment utilisés comprennent :

Les interpréteurs de commandes C et Tcl ont une syntaxe très similaire à celle des langages de programmation du même nom, et les interpréteurs Korn et Bash sont des développements de l'interpréteur Bourne, lui-même basé sur le langage ALGOL et enrichi d'éléments provenant de plusieurs autres langages. Par ailleurs, les différents interpréteurs de commandes, ainsi que des outils comme awk , sed , grep , et BASIC , Lisp , C , etc., ont contribué au développement du langage de programmation Perl .

Parmi les coquillages autrefois populaires, on trouve :

  • Old shell ( osh), un «port de l'interpréteur de commandes standard de la sixième édition UNIX»
  • KornShell ( ksh), depuis largement remplacé par son successeur, le Z shell
  • Tenex C Shell ( tcsh) et son prédécesseur, le C shell ( csh)

Des programmes connexes tels que des shells basés sur Python , Ruby , C , Java , Perl , Pascal , Rexx , etc., sous diverses formes, sont également largement disponibles.

Les shells distants, tels que

Ce ne sont en réalité que des outils permettant d'exécuter un shell plus complexe sur un système distant et ils ne possèdent pas eux-mêmes de caractéristiques de type « shell ».

Autres langages de script

De nombreux langages de script puissants, tels que Rexx, Python, Perl et Tcl, ont été introduits pour traiter des tâches trop importantes, complexes ou répétitives pour être gérées confortablement par des scripts shell traditionnels, tout en évitant la surcharge associée aux langages compilés comme C ou Java.

Bien que la distinction entre langages de script et langages de programmation de haut niveau à usage général soit souvent débattue, les langages de script se caractérisent généralement par leur interprétation, leur syntaxe simplifiée et leur utilisation principale pour l'automatisation des tâches, la coordination des opérations système et l'écriture de code d'interface entre les composants. Même lorsque des langages de script tels que Python, Rexx ou JavaScript prennent en charge la compilation en bytecode ou utilisent la compilation JIT pour améliorer les performances, ils sont encore couramment désignés comme « langages de script » en raison de leur association historique avec l'automatisation, les outils légers et les environnements de script plutôt qu'avec le développement d'applications autonomes.

Le scripting est une forme de programmation . Si le terme « scripting » peut mettre l’accent sur une automatisation légère et orientée tâches, le terme plus général de « programmation » englobe à la fois le scripting et le développement logiciel dans des langages compilés ou structurés. Ainsi, le scripting consiste à écrire du code pour indiquer à un ordinateur d’effectuer des tâches spécifiques, ce qui correspond à la définition fondamentale de la programmation.

Cycle de vie

Les scripts shell constituent souvent une étape initiale du développement logiciel et sont fréquemment convertis ultérieurement vers une implémentation sous-jacente différente, le plus souvent en Perl , Python ou C. La directive d'interprétation permet de masquer entièrement les détails d'implémentation au sein du script, plutôt que de les exposer via une extension de fichier, et assure une réimplémentation transparente dans différents langages sans impact pour les utilisateurs finaux.

Bien que les fichiers portant l' extension « .sh » soient généralement des scripts shell, la plupart des scripts shell n'ont pas d'extension.

Avantages et inconvénients

L'un des principaux avantages de l'écriture d'un script shell réside dans le fait que les commandes et la syntaxe sont identiques à celles saisies directement en ligne de commande. Le programmeur n'a pas à adopter une syntaxe totalement différente, comme ce serait le cas si le script était écrit dans un autre langage ou s'il utilisait un langage compilé.

Écrire un script shell est souvent bien plus rapide que d'écrire le code équivalent dans d'autres langages de programmation. Parmi ses nombreux avantages, citons la sélection aisée des programmes ou des fichiers, le démarrage rapide et le débogage interactif. Un script shell permet d'enchaîner les actions et de prendre des décisions au sein de programmes existants. Pour les scripts de taille moyenne, l'absence d'étape de compilation est un atout. L'exécution interprétative facilite l'intégration de code de débogage dans un script et sa réexécution pour détecter et corriger les bogues. Les utilisateurs non experts peuvent utiliser les scripts pour personnaliser le comportement des programmes, et les scripts shell offrent des possibilités, certes limitées, de multiprocessing.

En revanche, les scripts shell sont sujets à des erreurs coûteuses. Les fautes de frappe involontaires, comme rm -rf * /`ls` (au lieu de `ls` rm -rf */), sont monnaie courante dans la communauté Unix ; un simple espace en trop transforme la commande, qui supprime tous les sous-répertoires du répertoire courant, en une commande qui supprime tout le contenu du répertoire racine du système de fichiers . Des problèmes similaires peuvent transformer des commandes cpcomme `ls` et mv`ls` en armes redoutables, et une mauvaise utilisation de la >redirection peut supprimer le contenu d'un fichier.

Un autre inconvénient majeur réside dans la lenteur d'exécution et la nécessité de lancer un nouveau processus pour presque chaque commande shell. Lorsqu'un script peut être exécuté via un pipelinedes filtres efficaces prennent en charge la majeure partie du travail, le ralentissement est atténué. Toutefois, un script complexe est généralement plusieurs ordres de grandeur plus lent qu'un programme compilé classique effectuant une tâche équivalente.

Il existe également des problèmes de compatibilité entre les différentes plateformes. Larry Wall , créateur de Perl , a écrit cette phrase devenue célèbre : « Il est plus facile de porter un shell qu’un script shell. »

De même, les scripts plus complexes peuvent se heurter aux limitations du langage de script shell lui-même ; ces limitations rendent difficile l’écriture de code de qualité, et les extensions apportées par divers shells pour atténuer les problèmes du langage shell d’origine peuvent aggraver ces problèmes.

De nombreux inconvénients liés à l'utilisation de certains langages de script sont dus à des défauts de conception au sein de la syntaxe ou de l'implémentation du langage, et ne sont pas nécessairement imposés par l'utilisation d'une ligne de commande textuelle ; il existe un certain nombre de shells qui utilisent d'autres langages de programmation shell ou même des langages à part entière comme Scsh (qui utilise Scheme ).

Interopérabilité entre les langages de script

De nombreux langages de script partagent une syntaxe et des fonctionnalités similaires du fait de leur conformité à la norme POSIX , et plusieurs interpréteurs de commandes proposent des modes d'émulation ou de compatibilité. Cela permet souvent aux scripts écrits pour un interpréteur de commandes de s'exécuter dans un autre avec des modifications minimes.

Par exemple, Bash prend en charge une grande partie de la syntaxe originale du shell Bourne et propose un mode conforme à POSIX pour une meilleure portabilité. Cependant, Bash inclut également un certain nombre d'extensions absentes de POSIX, communément appelées « bashismes » . Bien que ces fonctionnalités améliorent les capacités de script, elles peuvent réduire la compatibilité avec d'autres shells comme Dash ou ksh .

Scripting shell sur d'autres systèmes d'exploitation

Les logiciels d'interopérabilité tels que Cygwin , MKS Toolkit , Interix (anciennement intégré aux services Microsoft Windows pour UNIX), Hamilton C shell et UWIN (AT&T Unix pour Windows) permettent d'exécuter des programmes shell Unix sur les systèmes Windows NT, même si certaines fonctionnalités peuvent ne pas être entièrement prises en charge sur les anciennes plateformes MS-DOS / Windows 95. Les versions antérieures de MKS Toolkit offraient également une compatibilité avec OS/2.

Les langages de script sont, par définition, extensibles. Sous Unix et autres systèmes conformes à la norme POSIX , awk et sed permettent d'étendre les capacités de traitement des chaînes de caractères et des nombres des scripts shell. Tcl , Perl, Rexx et Python disposent de bibliothèques graphiques et peuvent être utilisés pour coder des fonctions et des procédures pour les scripts shell, qui constituent un goulot d'étranglement en termes de performances (C, Fortran, l'assembleur, etc., sont encore bien plus rapides). Ils permettent également d'ajouter des fonctionnalités absentes du langage shell, telles que les sockets et autres fonctions de connectivité, le traitement de texte intensif, la manipulation de nombres si le script appelant ne les prend pas en charge, l'écriture et la modification automatiques de code, des techniques comme la récursivité , l'accès direct à la mémoire, différents types de tri , etc. Ces fonctionnalités sont difficiles, voire impossibles, à implémenter dans le script principal. Visual Basic pour Applications (VBA ) et VBScript permettent de contrôler et d'interagir avec des éléments tels que des tableurs, des bases de données, des programmes scriptables de tous types, des logiciels de télécommunications, des outils de développement, des outils graphiques et d'autres logiciels accessibles via le modèle objet composant ( COM ).