Le script en PERL

Les Commandes

Les commandes d'entrée/sortie

Premier point de détail vital à la bonne marche du script PERL : un point-virgule (;) est nécessaire après chaque ligne d'instruction. 

print

Equivalent de echo en BASH, print permet d'écrire une chaîne de caractères dans un  output. Principale différence, la façon de spécifier la sortie en question.

La syntaxe par défaut est :

print FILE "chaîne de caractères" ;

ou

print(FILE, "chaîne de caractères");

    FILE désigne un  FILEHANDLER.

Cet élément (le filehandler) est facultatif.
En son absence, la chaîne de caractères sera écrite dans l'output par défaut (la console Cygwin, en l'occurence)

 

filehandler (manipulateur de fichier)

Perl utilise un système appelé filehandler pour lire et écrire dans des fichiers.
Ce système passe par deux fonctions (en plus de print, ci-dessus):

open(FILE,"kiwigood.txt");

Cette fonction ouvre un filehandler sous le nom FILE. Ce filehandler pointera vers le fichier kiwigood.txt et gèrera le type d'accès autorisé sur ce fichier.
la fonction open autorise par défaut un accès en lecture seule.
    Si l'on veut un accès en écriture, par exemple, on écrira :

     open(FILE,">kiwigood.txt");

    Notez le > ajouté au début du nom de fichier : il indique l'accès en écriture.
    Pour un accès en ajout, on utilisera >>.

close(FILE);

Ferme le filehandler FILE. Le fichier lié n'est plus utilisable jusqu'à réouverture d'un filehandlerpointant vers lui.
ATTENTION : La fin d'une procédure ferme automatiquement tout filehandler utilisé par elle. La solution consiste en une utilisation répétée de la fonction open (à chaque début de procédure, en fait).

@ARGV

@ARGV (en majuscules) est un tableau spécial. Lorsqu'on lui assigne un fichier, il prend une ligne du fichier par cellule. @ARGV s'emploie en coordination avec l'opérateur diamant <>
Détail pratique : @ARGV ne nécessite pas d'utilisation préalable de la fonction open.

<>, l'opérateur diamant

<> fait appel au fichier stocké dans @ARGV, et ce ligne après ligne.
Par exemple :
   
    @ARGV="ratatouille.txt"
    while($ligne=<>)
    {
        INSTRUCTIONS
    }

exécutera le jeu d'instructions entre accolades pour chaque ligne de ratatouille.txt, préalablement stockée pour manipulation dans la variable $ligne.

Les structures conditionelles

if then elsif...

Then est facultatif. La structure case n'existe pas en Perl. Elle est remplacé par un bloc du genre if elsif elsif... else :

if(condition)
{
    instruction1;
    instruction2;
}
elsif(condition2)
{
    instruction3;
}
elsif(condition3)
{
    instruction4;
}
else
{
    instruction par défaut;
}

ATTENTION : un test d'égalité se fait avec un double égal (==). L'utilisation d'un égal simple assigne une valeur à une variable, entraînant un test toujours réussi.

while [...] do {...} 

Le done utilisé en bash pour marquer la fin du jeu d'instructions est rendu obsolète et remplacé par des accolades délimitant ledit jeu d'instructions.

La gestion des chaînes de caractères

substr

La commande  substr va récupérer une sous-chaîne dans une chaîne.
Elle est la raison du portage du projet sous Perl, car elle est native à ce langage, donc parfaitement supportée par toutes les versions de Perl, alors qu'elle posait problème sur certaines versions de Cygwin.

    substr($string,2,3);
renvoie la chaîne partant du caractère 2 sur une longueur de 3 caractères caractères dans $string. On compte les caractères en partant de zéro. En clair :
   
    substr("bonjour",2,3); renverra "njo".

Mais nous nous sommes aperçus qu'en fait, substr n'a que peu d'utilité dans le cas présent. Quitte à utiliser Perl au lieu de bash, nous avons  remplacé substr par une expression régulière (voir ci-dessous).

les expressions régulières : if($string=~/expreg/)

Dans tout test, si la condition porte sur une chaîne de caractères, on peut la tester via une expression régulière.
Ceci permet de ne pas amputer ou triturer sa chaîne avant de la traiter dans la condition. Par exemple, si l'on veut savoir si une chaîne commence par "http", il est plus intéressantd'écrire :

    if($chaine=~/^[http]/)
    {
        instruction;
    }

que de rajouter une variable qui récupère les 4 premiers caractères de $chaine via substr avant de faire un test rigide (la syntaxe des expressions régulières permet au besoin d'ignorer la casse, de différencier ou non lettres et chiffres, et pas mal d'autres flexibilités).
Un test sur expression régulière est annoncé par =~ au lieu de ==. Et l'expression elle-même est délimitée par des slashs '/' .

On peut modifier ladite expression de nombreuses façons qu'il serait fastidieux d'expliquer ici (elles sont vraiment nombreuses).
Citons seulement celles utilisées :

/expression/i : un i (pour "ignore") accolé au slash fermant permet d'ignorer la casse. Majuscules comme minuscules seront prises en compte.

$var=~s/expression/modif/; : le s (pour "switch") précédant le slash ouvrant permet de transformer le contenu de la variable correspondant à 'expression' en 'modif'.
Par exemple :
$var=~s/bonjour/Bonjour !/i;
permet d'assigner la chaîne "Bonjour !" à la variable $var si elle contient au départ "bonjour" sous n'importe quelle casse (bonjour, BoNjOuR, bonJour,Bonjour...).
Ceci ne vaut que pour le premier "bonjour" de la chaîne.

Si l'on rajoute g juste après l'expression régulière, on prend en compte toutes les itérations correspondant à cette expression. En clair, si on entre :
$var=~s/toto/Toto/ig;
Chaque "toto", "ToTo", "Toto", etc... contenu dans $var sera remplacé par un "Toto". Si on n'avait pas mi le g, seul le premier "toto" de la chaîne aurait été affecté.

L'antislash permet comme souvent d'échapper un caractère, de le prendre tel quel.
Par exemple, si l'on veut prendre en compte un caractère slash dans une expression régulière, il faut le précéder d'un antislash... ce qui peut occasionner des expressions régulières en dents de scie. 
Exemple extrait de notre script :
elsif($ligne=~/^http:\/\/*/)
Pour éviter ces dents de scie (rendant l'expression peu lisible), on peut redéfinir le caractère délimitant l'expression régulière en faisant précéder l'expression de la lettre m.
exemple : $ligne=~m%^http://*%; (ici, '§' est devenu le carctère délimitant, on a donc plus à discriminer les '/').

Les commandes de récupération Cygwin

 identiques à celles utilisées en bash, elles doivent être incluses dans la fonction system.

system( fonction_système);

La commande system permet d'utiliser une fonction ou un outil intégré au système (ici, Cygwin).
Par exemple, pour utiliser lynx, on écrira :
    system("lynx -dump $destination > $dumpdest");

avec $destination qui contient l'url cible et $dumpdest qui contient le fichier .txt qui doit recevoir le texte dumpé.

les procédures

sub func() {}

    sub func()
    {
        INSTRUCTIONS
    }

crée une fonction func qui, lorsqu'elle sera appelée exécutera le jeu d'instructions compris entre accolades.

&func;

    &func;

appelle la fonction func.
Si des arguments sont nécessaires à l'utilisation de ladite fonction, la syntaxe sera :
    &func(arg1,arg2,...,argN);