PowerShell: Simplifier la création de fonction avec les bons arguments

Depuis l’arrivée de SharePoint 2010, l’utilisation de PowerShell est devenue presque incontournable. Pour industrialiser certaines procédures, il n’est pas rare de créer des fonctions utilitaires, pour modulariser ses scripts et parfois même étendre la console PowerShell avec des modules personnalisés.

L’article d’aujourd’hui a pour objectif de vous montrer comment créer des fonctions plus simples à utiliser, en jouant avec le typage des paramètres.

Tout d’abord, prenons une fonction “classique”, sans enrichissement des paramètres :

Premier problème: les arguments ne sont pas vérifiés

Vous pouvez passer n’importe quoi à cette fonction, mais sans avoir d’information sur éventuelle erreur. Tout ces appels vont “passer” :

Toutefois, aucun de ces appels ne va montrer que quelque chose ne va pas.

Modifions notre fonction pour lui ajouter la définition des paramètres et rendre obligatoire le paramètre $web :

Le résultat des mêmes appels que précédement :

On progresse. Maintenant, la fonction ne s’exécute pas si $web vaut null.

Deuxième problème: les arguments ne sont pas typés

Comme vous l’avez vu, l’argument $web doit être présent. Mais rien n’empêche de passer autre chose qu’un SPWeb !

Modifions encore notre fonction pour ajouter le typage du paramètre :

On est maintenant obligé de passer un objet de type SPWeb pour que la fonction passe

Troisième problème: l’utilisateur est obligé d’avoir un objet de type SPWeb

Ce n’est pas vraiment un problème technique, mais une question de confort d’utilisation. L’utilisateur peut vouloir appeler cette fonction avec un objet SPWeb, ou aussi une simple chaîne de caractère contenant l’url. Comme le montre les exemples ci dessus, passer “http://localhost” n’est pas reconnu.

Heureusement Microsoft fourni, pour les principaux objets gérable dans PowerShell des équivalent “*PipeBind”. Par exemple, la classe “Microsoft.SharePoint.PowerShell.SPWebPipeBind” permet de passer différentes formes de réprésentation d’un SPWeb.

En effet, cette classe définit les constructeurs suivants :

On peut en conclure que l’on peut passer soit un objet SPWeb directement, soit un ID, son url sous forme de chaine ou son url sous forme d’Uri.

Notre fonction transformée deviendra donc:

Notez la différence dans le corps de la fonction, notamment l’appel à la méthode “Read()” sur l’objet PipeBind

Avec comme résultats :

Cette fois ci, l’appel avec la simple url du site aura fonctionné!

Quatrième problème: la fonction ne peut être utilisée dans le pipe

L’une des principales fonctionnalités de PowerShell est de proposer un pipeline. Aussi, il est naturel de vouloir utiliser la syntaxe suivante :

En l’état, la fonction va demander à l’utilisateur de saisir la valeur de l’argument $web en ignorant totalement le contenu du pipeline.

Modifions encore une fois notre fonction pour extraire du pipeline cet argument :

L’attribut “ ValueFromPipeLine” indique à PowerShell d’extraire la valeur de l’argument à partir du Pipeline. Le résultat est alors celui escompté :

Conclusion: des meilleures fonctions!

Avec un peu d’habitude, vous améliorerez la qualité de vos fonctions. Non pas dans leur corps, mais dans la façon de les appeler. Correctement définir les paramètres permet de déceler certains problèmes en amont (typage, nullité, etc.). Hors, comme vous le savez, plus tôt ça “plante” mieux on se porte 🙂

Rating 4.33 out of 5
[?]