PI Services

Le blog des collaborateurs de PI Services

Migration vers SharePoint 2010 avec AvePoint

 

De plus en plus d’entreprise ayant choisit MOSS 2007 pour répondre à leur besoin en terme de travail collaboratif commencent à migrer vers la solution SharePoint 2010 afin de bénéficier de toutes les nouveautés et des améliorations du produit.

Microsoft propose nativement quelques méthodes de migration, chacune de ces méthodes possèdent des avantages et des inconvénients.

La migration peut être découpée en deux étapes importantes : migration de la version de l’outil SharePoint (Déploiement de SharePoint 2010 sur tous les serveurs de la ferme) et la migration du contenu du portail existant SharePoint.

Ave Point propose son outil Doc Ave SharePoint Migrator V5 permettant de migrer le contenu SharePoint d’une ferme à une autre.

Voici la liste des éléments pouvant être migrés :

  • Les bibliothèques 
  • Les dossiers
  • Les pages Web
  • Les listes
  • Les différentes versions des documents (si le versionning est activé sur le site SharePoint)
  • La Sécurité : utilisateurs et permissions
  • Les listes personnalisées
  • Les métadatas
  • Les modèles de sites
  • Mes Liens

Avantages de l’utilisation de cet outil :

  • Minimiser les efforts requis pour le déploiement de la nouvelle version de SharePoint : puisque DocAve permet de déplacer automatiquement le contenu source vers le contenu Cible en gardant les mappages des éléments ainsi que toutes les propriétés.
  • DocAve assure l’intégrité des données sensibles durant la migration.
  • Réutilisation des sauvegardes SharePoint pour faciliter la migration : Lors d’une migration il est possible soit de migrer le contenu directement (en Live) soit de faire une restauration à partir de sauvegardes existantes, dans ce 2e cas l’administrateur optimise sa productivité puisqu’il n’aura pas à recréer la structure de la plateforme.
  • Permet aux administrateurs SharePoint de réussir leur Migration en évitant d’oublier des étapes à exécuter.
  • Avec DocAve Migrator, la migration en direct est très simple et se base sur un simple glissé/deplacé ce qui par conséquent simplifie la migration
  • Flexibilité de la migration : Avec docAve Migrator, la migration peut se faire de manière granulaire (une instance, un dossier, ou un élément…) et peut être planifiée (exécution de la tâche de migration à une heure précise).
  • L’outil DocAve Migrator peut être deployé sur un matériel existant de la plateforme SharePoint existante, aucun pré requis matériel n’est obligatoire
  • DocAve Migrator, utilise un scanner de pré migration afin d’éviter tout risque d’erreur.

Les ressources pouvant être migrées avec DocAve Migrator vers SharePoint 2010:

  • SharePoint 2001, 2003, 2007
  • Exchange Public Folder
  • File Systems/Network Shares
  • Documentum/eRoom
  • Open Text Livelink/Vignette
  • Lotus Notes/QuickPlace
  • Oracle Stellent
  • Static, HTTP/S accessible web content and internet sites
  • Microsoft Content Management Server 2002 (MCMS 2002)

EXCHANGE 2010 – Gestion des groupes de distributions

Pour rappel sous Exchange 2010 il ne suffit pas de mettre un gestionnaire

pour lui permettre de gérer un groupe de distribution:

image

Il faut activer le rôle défini par le mécanisme RBAC.

Cochez “MyDistributiongroups”

image

On constate en lançant Outlook Web App que la création de groupe

n’est pas disponible avant l’activation du rôle:

image

Après activation, de nouveaux menus sont disponibles:

image

Chaque utilisateur peut donc créer un groupe

et supprimer un groupe dont il est le propriétaire !

Ce droit “excessif” peut ne pas répondre à la stratégie de la société.

Nous allons donc retirer ces droits de création et de suppression.

Recherchons le rôle “MyDistributionGroups”

image

Créer un rôle enfant de “MyDistributionGroups” en supprimant le droit de créer et de supprimer un groupe.

New-ManagementRole –Name ****OwnerDistributionGroups -Parent MyDistributionGroups

image

image

On remarque la présence de ce nouveau rôle dans la console “RBAC”:

image

Vérifions le rôles assignés sur “Default Role Assignment Policy”

image

MyDistributionGroups est présent.

Supression des droits New et Remove

Remove-ManagementRoleEntry ****OwnerDistributionGroups\New-DistributionGroup -Confirm:$false

Remove-ManagementRoleEntry ****OwnerDistributionGroups\Remove-DistributionGroup -Confirm:$false

Puis il faut associer le “Default Default RoleAssignment Policy” avec ce nouveau rôle :

New-ManagementRoleAssignment –Role ****OwnerDistributionGroups -Policy "Default Role Assignment Policy"

image

L’opération n’est pas finie car le rôle parent est toujours assigné donc actif.

Supprimons ce lien:

Remove-ManagementRoleAssignment “MyDistributionGroups-Default Assignment Policy”

image

Vérifions

image

Ce qui donne dans la console RBAC cette configuration:

image

Et pour l’utilisateur final:

image

Les droits de création et de suppression ne sont plus disponible.

Windows échoue à se connecter à l’imprimante

Symptômes :

Lors du rapatriement des pilotes un bug se produit et l’assistant s’interrompt (imprimante réseau couleur).

« Windows cannot connect to the printer. Operation failed with error 0x0000007e ».

imageimage

                            image

Ce problème survient lorsque qu’on tente d’ajouter une imprimante couleur sur un poste client Windows 7 rattaché à un serveur d’impression Windows 2003 ou Windows 2008.

Deux solutions de contournements fonctionnent car le problème est connu par Microsoft mais sans correctif pour le moment.

· Le premier s’opère sur le poste client, et consiste à installer l’imprimante en utilisant le port LPT2, puis d’utiliser une commande de redirection

                             clip_image002

· Le deuxième consiste à modifier une clé de registre sur le serveur d’impression. Puis de se connecter à l’imprimante.

Regedit> HKLM\System\CurrentControlSet\Control\Print\Printers\printername\CopyFiles en renommant le répertoire CopyFiles par xCopyFiles. Ce répertoire n’existe que pour une imprimante couleur.

clip_image003

Les deux solutions fonctionnent instantanément. Mais il est beaucoup plus rapide de modifier le répertoire défaillant directement dans la base de registre pour toutes les imprimantes concernées.

Manipulation des droits NTFS via Powershell

Il existe un module nommé NTFSSECURITY permettant une manipulation simplifié des droits NTFS sur des dossiers et/ou fichiers.

Ce module peut être trouvé sur la galerie Technet http://gallery.technet.microsoft.com/scriptcenter/1abd77a5-9c0b-4a2b-acef-90dbb2b84e85/file/48905/1/NTFSSecurity%201.3.zip

 

Une fois téléchargé, mettez le dossier du module NTFSSecurity ici C:\Windows\System32\WindowsPowerShell\v1.0\Modules

Maintenant, nous allons charger le module dans powershell

image

Une fois celui-ci chargé, de nouvelles cmdlets sont désormais disponible.

image                                   

Récupération du SID d’un utilisateur dans une variable.

Nous allons définir dans une variable $SamMember le nom de l’utilisateur que nous voulons récupérer.

Ensuite nous allons utiliser l’object System.Security.principal.NtAccount(« domaine »,utilisateur) qui va nous permettre de récupérer notre utilisateur dans un domaine spécifié.

image

image

Maintenant, récupérons le SID de notre utilisateur grâce à une méthode de notre variable $account.

image

Nous avons ainsi récupéré dans notre variable $accountsid le SID de notre utilisateur spécifié dans la variable $SamMember.

 

Modification du propriétaire d’un répertoire.

Avec le chargement du module NTFSSecurity, une cmdlet get-owner est apparue nous permettant de connaitre simplement le propriétaire d’un élément (fichier ou répertoire).

Exemple :

image

Nous allons maintenant changer le propriétaire de ce répertoire avec l’utilisateur contenu dans notre variable $accountsid

image

Voyons maintenant le résultat :

image

 

Le propriétaire à bien été changé.

 

Modification des ACE du répertoire.

Nous allons maintenant modifier les ACE du répertoire de façon à ne laisser que l’utilisateur de notre variable $accountsid en FullControl et aucune autre ACE.

Rajout de l’ACE :

image

Suppression des autres ACE :

image

(Ce lien permet de connaitre les SID connu dans les OS Windows http://support.microsoft.com/kb/243330)

 

Si on consulte maintenant nos ACE, on peut remarquer que notre ajout d’ACE s’est bien passé mais que la suppression des autres ACE ne s’est pas déroulée correctement.

 

image

Cela est normal, car ses ACE sont hérité du répertoire parent. Il faut donc pour cela retirer l’héritage.

clip_image001[4]

Et maintenant si on essaie de nouveau de supprimer nos ACE on peut remarquer que celle-ci ont bien disparu.

 

image

Il est maintenant facile d’imaginer la création d’un script pouvant réappliquer correctement des droits sur une toute une arborescence de répertoires profils en récupérant par exemple le nom du répertoire profil et en réaffectant celui-ci dans une boucle pour notre variable $account.

 

image

 

clip_image005

Ainsi, l’utilisateur authentifié en user2, ne pourra accéder qu’à son répertoire profil.

Traitement des utilisateurs sous USMT en mode Offline

 

Le comportement d’USMT dans un état Offline est différent d’un état Online.

Nous nous situons dans un cas ou l’exécutable Scanstate est lancé sous Windows PE (donc offline).

Lors d’une capture en offline, le mappage des utilisateurs ne peut se baser sur la base SAM des utilisateurs. Le mappage s’effectue à l’aide des SID.

 

Exemple du log du ScanState sous Windows PE (Offline)

image

Exemple du log de ScanState sous Windows XP (Online)

image

 

Ce qui veut dire que pendant l’utilisation du ScanState sous Windows PE, nous ne devons travailler qu’avec des SID.

Si par exemple on ne veut inclure qu’un seul utilisateur dans notre DataStore du ScanState, il faudra utiliser l’argument /ue:* permettant d’exclure tous les utilisateurs et utiliser l’argument /ui  permettant d’inclure l’utilisateur spécifique avec son SID.

Exemple:

scanstate E:\Migshare\U11281 /i:x:\ftmas7\tools\usmt\F2_MigFiles.xml /i:x:\ftmas7\tools\usmt\MigOutlook.xml /o /c /localonly /v:13 /offlinewindir:c:windows /ue:* /ui:S-1-5-21-1221297486-3643808661-2871141796-1074 /l:E:\Migshare\U11281\log.txt

Pour inclure plusieurs utilisateurs, l’argument /ui peut être utilisé autant de fois que désiré.

Utilisation du ScanState en Offline pour capturer uniquement des utilisateurs du domaine.

Si vous souhaitez ne capturer que des utilisateurs d’un domaine et non les utilisateurs locaux, vous pouvez exclure tout le monde via l’argument /ue :* et inclure uniquement le SID du domaine avec l’astérique « * » pour le pool RID.

Exemple :

scanstate.exe S: /i:MigFiles.xml /i:MigOutlook.xml /l:S:\log.log /progress:S:\Prog.log /localonly /o /c /v:13 /offlinewindir:c:\windows /ue:* /ui: S-1-5-21-759407729-413330662-2607319723-"*"

 

Utilisation du LoadState sur un DataStore obtenu par un ScanState Offline

Contrairement au ScanState, le LoadState ne peut être exécuté qu’en mode Online.

Ayant utilisé ScanState en mode Offline, nous avons donc du traiter les utilisateurs via leurs SID. Il en sera donc de même pour le LoadState car aucun mappage samaccountname n’a pu être effectué précédemment.

Donc l’utilisation des commutateurs /ue et /ui se passent de la même manière que pour le Scanstate en Offline c’est-à-dire basé sur des SID.

Dans le cas d’une migration de domaine, il n’est pas nécessaire de spécifier le SID du domaine source vers le domaine cible. (La migration de domaine s’opère à l’aide du commutateur /md. (/md:Old_domain :New_domain)

Exemple :

loadstate F:\Migshare\U11281 /i:C:\APPLI_FTV\apps\usmt\F2_MigFiles.xml /i:C:\APPLI_FTV\apps\usmt\MigOutlook.xml /c /v:13 /l:F:\Migshare\U11281\Load-log.txt /md:SourceSI :CibleSi /progress:F:\Migshare\U11281\simpleprog.log

Cela signifie que tous les utilisateurs situés dans le DataStore avec pour domaine source « SourceSI » vont être migré sur « CibleSi » si ceux-ci existent.

Attention, si USMT tente de migrer un utilisateur sur un domaine cible mais que celui-ci n’existe pas dans ce domaine, une erreur fatale en ressortira et le déroulement du LoadState sera alors interrompu.

Cependant, si vous souhaitez utiliser /mu au lieu de /md, la, il faudra utiliser le SID utilisateur depuis la source et spécifier le domaine cible ainsi que son Sam Account Name.

Exemple :

loadstate F:\Migshare\U11281 /i:C:\APPLI_FTV\apps\usmt\F2_MigFiles.xml /i:C:\APPLI_FTV\apps\usmt\MigOutlook.xml /c /v:13 /l:F:\Migshare\U11281\Load-log.txt /mu:S-1-5-21-1221297486-3643808661-2871141796-1074:CibleSi\trsb2 /ui:S-1-5-21-1221297486-3643808661-2871141796-1074 /progress:F:\Migshare\U11281\simpleprog.log /ue:*

Le profil utilisateur sera alors créé sur l’os cible dans le nouveau domaine.

Vérification d’utilisateurs existant dans un domaine en Powershell

Vous disposez d’une liste exhaustive de comptes utilisateurs dans un fichier et vous désirez savoir ceux d’entre eux qui sont bien existant dans le domaine courant.

Pour cela, nous allons parcourir ce fichier et établir une connexion sur ces utilisateurs. Si la connexion sur l’utilisateur se passe bien, nous l’ajouterons dans un second fichier. Si cet utilisateur n’existe pas, nous l’ignorerons.

Exemple de fichiers contenant sur une colonne des utilisateurs existant ou non dans le domaine courant.

image

image

 

image

Résultat obtenu dans un fichier result.txt :

image

Le script nous a bien permit de récupérer uniquement les utilisateurs existant dans le domaine courant.

SCOM 2007 R2 – Créer une tâche console avec la console authoring

Les « tâches console » sont comme leur nom l’indique des tâches qui s’exécutent sur la console, par opposition aux tâches Agent qui sont elles exécutées sur les ordinateurs monitorés et dont le résultat est ensuite affiché dans la console.

Elles permettent de lancer un exécutable sur l’ordinateur exécutant la console, éventuellement en lui passant des paramètres récupérés dans la console.

Exemple concret : on peut ainsi lancer un ping ou une session bureau à distance automatiquement vers le l’ordinateur sélectionné dans  la console.

Je détaillerai ici le cas rencontré chez un client qui souhaitait pouvoir accéder aux incidents créés indépendamment de SCOM dans un système de gestion de tickets tiers à la suite de la remontée de certaines alertes dans SCOM.
Ce système de ticket étant accessible via un simple navigateur web sur une url fixe prenant l’ID du ticket en paramètre (ID préalablement renseignée dans un CustomField de l’alerte par le helpdesk), nous avons procédé de la sorte :

Dans la console Authoring (et non pas la vue authoring de la console Operations, cette dernière ne permet pas de créer ce genre de tâche!), créer un nouveau management pack.
Se rendre dans la vue Presentation et sélectionner Console Tasks dans le menu de gauche, puis faire un clic-droit à sélectionner New>Console Task (attention à ne pas confondre avec les Agent Tasks qui se trouvent elles dans la vue Health Model!) :

image

Nommer cette nouvelle tâche :

image

Lui donner un nom d’usage, qui apparaitra dans SCOM et choisir l’élément qu’elle ciblera :

image

 

Dans l’onglet Command Line, renseigner la partie fixe de la commande lancée par la tâche.
Dans notre cas il s’agit donc d’appeler le navigateur web et de lui passer la partie invariable de l’URL du système de gestion de tickets, mais plutôt que d’indiquer le chemin absolu vers l’exécutable du browser, nous avons choisi d'appeler le navigateur par défaut du système à l’aide du raccourci rundll32 url.dll,FileProtocolHandler http://suivi.tickets.local/?ticketID= .
Cela permet d’éviter les potentiels soucis liés à l’utilisation de navigateurs différents suivant les ordinateurs et respecte ainsi les préférences de l’utilisateur de la console SCOM.
Il faut ensuite indiquer en paramètre que l’on souhaite récupérer le CustomField de l’alerte contenant l’ID du ticket.
Oui mais… par défaut, seul le Display Name est disponible en paramètre :

image

 

Afin de modifier ce comportement, se rendre dans l’onglet Options et cliquer sur Category [Value=MonitoringObject]. Cela dévoile des options qui étaient jusque là invisibles et il est alors possible de sélectionner la catégorie Alert :

image

 

En retournant dans l’onglet CommandLine, on constate qu’il est maintenant possible de sélectionner les CustomField  comme paramètres (ainsi que bien d’autres, libre à vous d’adapter suivant vos besoins!) :

image

 

Il ne reste plus qu’à enregistrer le management pack et à le publier dans SCOM.

Script Powershell – Desinstallation d’application

 

Le script suivant prends en paramètre un nom de machine et un nom d’application (apparaissant dans Ajout-suppression de programme), desinstalle l’application si elle est trouvée, affiche les resultats et les inscris dans un fichier de log.

 

 

Param(
[Parameter(Mandatory = $true)][string]$computername=(read-host -Prompt "entrez le nom de la machine"),
[Parameter(Mandatory = $true)][string]$application=(read-host -Prompt "entrez le nom exact de l'application"),
[string]$credential="administrator"
)

$logfile="c:\result.txt"
$now=(get-date).ToString()

$appuninstall=Get-WmiObject -ComputerName $computername -Class win32_product -Credential $credential | where-object {$_.name -eq $application}

if ($appuninstall -eq $null)
{
write-host "Application $application non trouvée" -ForegroundColor yellow -BackgroundColor black
write-host "Resultat inscris dans $logfile" -ForegroundColor yellow -BackgroundColor black
Out-file $logfile -Append -InputObject "$now -- Application $application non trouvée sur $computername"
exit
}

foreach ($app in $appuninstall)
{
  write-host "...debut desinstallation..." -ForegroundColor yellow -BackgroundColor black
  $app.uninstall()| Tee-Object -Variable uninstallresult
if ($uninstallresult.ReturnValue -eq 0)
    {
    write-host "Desinstallation OK pour $computername" -ForegroundColor green -BackgroundColor black
    write-host "Resultat inscris dans $logfile" -ForegroundColor green -BackgroundColor black
    Out-file $logfile -Append -InputObject "$now -- Desinstallation OK pour $computername"
    }
    else
    {
    write-host "Desinstallation KO pour $computername" -ForegroundColor red -BackgroundColor black
    Out-file $logfile -Append -InputObject "$now -- Desinstallation KO pour $computername"
    write-host "Resultat inscris dans $logfile" -ForegroundColor red -BackgroundColor black
    }
}

BlogEngine.NET en Haute-Disponibilité

 

Présentation de BlogEngine.NET

BlogEngine.NET est une plateforme de blog open-source développé en C#, elle permet entre-autres la gestion des auteurs, des posts et ne requiert ni base de donnée ni installation.

Toutes les fonctionnalités ici.

Contexte

Pour la configuration de serveurs WEB en Haute-Dispo, il est possible de créer entre les serveurs une réplication des dossiers de BlogEngine à l’aide de DFS-R.

Suite à la mise en place de la réplication DFS-R entre les deux serveurs Web, une latence d’environ une heure lors de l’ajout (ou la modification) d’un post à partir d’un serveur et la visualisation sur le second est apparue.

Cette latence n’est pas due à DFS-R car au niveau du système il est visible que le post (enregistré au format XML) a correctement été répliqué.

Explication

Afin d’assurer un temps de réponse optimal, BlogEngine dispose d’un cache interne qui est mis à jour automatiquement.

Résolution

Pour de palier à ce problème il suffit de modifier la page default.aspx.cs située à la racine du répertoire de BlogEngine en ajoutant au début de la fonction Page_Load() la commande BlogEngine.Core.Post.Reload() comme ceci :

image

Ce qui permettra à chaque fois que l’utilisateur se connecte sur la page Accueil, de recharger le cache.

SCOM 2007 : Hériter des tâches depuis un MP parent

Ou comment séparer la définition de l’affichage des tâches.

Voici un problème qui m’a été posé par un de nos clients : comment réutiliser des tâches définies dans un premier Management Pack dans un ou plusieurs autres MP, sans avoir à les recoder à chaque fois ? Après recherche, voici la solution qui a été retenue.

Prenons un exemple simple : via la console Authoring, créons dans un nouveau management pack une tâche console qui lance la calculatrice Windows.

clip_image002

Une fois enregistré non-scellé, le code xml de ce management pack très basique est le suivant :

<ManagementPack ContentReadable="true" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<Manifest>
    <Identity>
      <ID>MP_ExempleTask</ID>
      <Version>1.0.0.0</Version>
    </Identity>
    <Name>MP_ExempleTask</Name>
    <References>
      <Reference Alias="Windows">
        <ID>Microsoft.Windows.Library</ID>
        <Version>6.1.7221.0</Version>
        <PublicKeyToken>31bf3856ad364e35</PublicKeyToken>
      </Reference>
      <Reference Alias="System">
        <ID>System.Library</ID>
        <Version>6.1.7221.0</Version>
        <PublicKeyToken>31bf3856ad364e35</PublicKeyToken>
      </Reference>
    </References>
  </Manifest>
  <TypeDefinitions>
    <ModuleTypes>
      <ProbeActionModuleType ID="calcType" Accessibility="Public" Batching="false" PassThrough="false">
        <Configuration />
        <ModuleImplementation Isolation="Any">
          <Composite>
            <MemberModules>
              <ProbeAction ID="PA" TypeID="System!System.CommandExecuterProbe">
                <ApplicationName><![CDATA[%WINDIR%\System32\calc.EXE]]></ApplicationName>
                <WorkingDirectory />
                <CommandLine>/ALL</CommandLine>
                <TimeoutSeconds>30</TimeoutSeconds>
                <RequireOutput>true</RequireOutput>
                <Files />
              </ProbeAction>
            </MemberModules>
            <Composition>
              <Node ID="PA" />
            </Composition>
          </Composite>
        </ModuleImplementation>
        <OutputType>System!System.PropertyBagData</OutputType>
        <InputType>System!System.BaseData</InputType>
      </ProbeActionModuleType>
    </ModuleTypes>
  </TypeDefinitions>
  <Presentation>
    <ConsoleTasks>
      <ConsoleTask ID="Task.LocalCalc" Accessibility="Internal" Enabled="true" Target="System!System.Entity" RequireOutput="true" Category="MonitoringObject">
        <Application>%systemroot%\system32\calc.exe</Application>
        <WorkingDirectory />
      </ConsoleTask>
    </ConsoleTasks>
  </Presentation>
  <LanguagePacks>
    <LanguagePack ID="FRA" IsDefault="false">
      <DisplayStrings>
        <DisplayString ElementID="MP_ExempleTask">
          <Name>MP Exemple Task</Name>
        </DisplayString>
      </DisplayStrings>
    </LanguagePack>
    <LanguagePack ID="ENU" IsDefault="true">
      <DisplayStrings>
        <DisplayString ElementID="Task.LocalCalc">
          <Name>Ouvrir Calculatrice</Name>
          <Description />
        </DisplayString>
        <DisplayString ElementID="MP_ExempleTask">
          <Name>MP Exemple Task</Name>
        </DisplayString>
      </DisplayStrings>
    </LanguagePack>
  </LanguagePacks>
</ManagementPack>

La suite de la manœuvre implique d’utiliser un éditeur de texte : il va falloir séparer les parties « manifest », « défintion » et « affichage » de votre management pack.

Le manifest est le code compris entre les balises <Manifest></Manifest> (surligné plus haut en vert) :

<Manifest>
    <Identity>
      <ID>MP_ExempleTask</ID>
      <Version>1.0.0.0</Version>
    </Identity>
    <Name>MP_ExempleTask</Name>
    <References>
      <Reference Alias="Windows">
        <ID>Microsoft.Windows.Library</ID>
        <Version>6.1.7221.0</Version>
        <PublicKeyToken>31bf3856ad364e35</PublicKeyToken>
      </Reference>
      <Reference Alias="System">
        <ID>System.Library</ID>
        <Version>6.1.7221.0</Version>
        <PublicKeyToken>31bf3856ad364e35</PublicKeyToken>
      </Reference>
    </References>
  </Manifest>

La partie définition est l’ensemble du code compris entre les balises <TypeDefinitions>[…]</TypeDefinitions> (surligné plus haut en bleu). C’est cette partie qui contient le code de « ce que font » les tâches à proprement parler :

<TypeDefinitions>
    <ModuleTypes>
      <ProbeActionModuleType ID="calcType" Accessibility="Public" Batching="false" PassThrough="false">
        <Configuration />
        <ModuleImplementation Isolation="Any">
          <Composite>
            <MemberModules>
              <ProbeAction ID="PA" TypeID="System!System.CommandExecuterProbe">
                <ApplicationName><![CDATA[%WINDIR%\System32\calc.EXE]]></ApplicationName>
                <WorkingDirectory />
                <CommandLine>/ALL</CommandLine>
                <TimeoutSeconds>30</TimeoutSeconds>
                <RequireOutput>true</RequireOutput>
                <Files />
              </ProbeAction>
            </MemberModules>
            <Composition>
              <Node ID="PA" />
            </Composition>
          </Composite>
        </ModuleImplementation>
        <OutputType>System!System.PropertyBagData</OutputType>
        <InputType>System!System.BaseData</InputType>
      </ProbeActionModuleType>
    </ModuleTypes>
  </TypeDefinitions>

La partie “affichage” est quant à elle celle qui est comprise entre les balises <Presentation>[…]</LanguagePacks> (surlignée plus haut en rouge). C’est cette partie qui se charge de faire apparaitre les tâches dans la console SCOM :

<Presentation>
    <ConsoleTasks>
      <ConsoleTask ID="Task.LocalCalc" Accessibility="Internal" Enabled="true" Target="System!System.Entity" RequireOutput="true" Category="MonitoringObject">
        <Application>%systemroot%\system32\calc.exe</Application>
        <WorkingDirectory />
      </ConsoleTask>
    </ConsoleTasks>
  </Presentation>
  <LanguagePacks>
    <LanguagePack ID="FRA" IsDefault="false">
      <DisplayStrings>
        <DisplayString ElementID="MP_ExempleTask">
          <Name>MP Exemple Task</Name>
        </DisplayString>
      </DisplayStrings>
    </LanguagePack>
    <LanguagePack ID="ENU" IsDefault="true">
      <DisplayStrings>
        <DisplayString ElementID="Task.LocalCalc">
          <Name>Ouvrir Calculatrice</Name>
          <Description />
        </DisplayString>
        <DisplayString ElementID="MP_ExempleTask">
          <Name>MP Exemple Task</Name>
        </DisplayString>
      </DisplayStrings>
    </LanguagePack>
  </LanguagePacks>

Vous avez isolé ces deux parties? Bien, nous allons pouvoir passer à la suite : il faut maintenant construire deux management packs séparés, et ce toujours à l’aide d’un éditeur de texte.
En toute logique, le premier contiendra la partie définitions et le second la partie affichage… ainsi que quelques subtilités :

Pour le premier, c’est assez simple. Créons un fichier texte que nous nommerons par exemple mp1.xml et copions-y la partie « définition » préalablement extraite, précédée du manifest, le tout encadré par les balises <ManagementPack> nécessaires à la conformité de tout MP :

<ManagementPack ContentReadable="true" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<Manifest>
    <Identity>
      <ID>MP1</ID>
      <Version>1.0.0.0</Version>
    </Identity>
    <Name>MP1</Name>
    <References>
      <Reference Alias="Windows">
        <ID>Microsoft.Windows.Library</ID>
        <Version>6.1.7221.0</Version>
        <PublicKeyToken>31bf3856ad364e35</PublicKeyToken>
      </Reference>
      <Reference Alias="System">
        <ID>System.Library</ID>
        <Version>6.1.7221.0</Version>
        <PublicKeyToken>31bf3856ad364e35</PublicKeyToken>
      </Reference>
    </References>
  </Manifest>
  <TypeDefinitions>
    <ModuleTypes>
      <ProbeActionModuleType ID="calcType" Accessibility="Public" Batching="false" PassThrough="false">
        <Configuration />
        <ModuleImplementation Isolation="Any">
          <Composite>
            <MemberModules>
              <ProbeAction ID="PA" TypeID="System!System.CommandExecuterProbe">
                <ApplicationName><![CDATA[%WINDIR%\System32\calc.EXE]]></ApplicationName>
                <WorkingDirectory />
                <CommandLine>/ALL</CommandLine>
                <TimeoutSeconds>30</TimeoutSeconds>
                <RequireOutput>true</RequireOutput>
                <Files />
              </ProbeAction>
            </MemberModules>
            <Composition>
              <Node ID="PA" />
            </Composition>
          </Composite>
        </ModuleImplementation>
        <OutputType>System!System.PropertyBagData</OutputType>
        <InputType>System!System.BaseData</InputType>
      </ProbeActionModuleType>
    </ModuleTypes>
  </TypeDefinitions>
</ManagementPack>

Notez que j’ai également modifié l’ID et le Nom de ce MP, qui s’appelle désormais “MP1”.

Une fois ce fichier XML achevé, il faudra le sauvegarder en tant que Management Pack scellé et noter sa clé publique ; autrement il ne sera pas possible de l’importer dans les MP qui devront y faire appel, puisqu’on ne peut pas hériter d’un MP non scellé.

Passons ensuite au MP2 : il contient également le Manifest (auquel j’ai apporté quelques modifications, détaillées plus bas), suivi cette fois uniquement de la partie affichage :

<ManagementPack ContentReadable="true" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<Manifest>
    <Identity>
      <ID>MP2</ID>
      <Version>1.0.0.0</Version>
    </Identity>
    <Name>MP2</Name>
    <References>
      <Reference Alias="Windows">
        <ID>Microsoft.Windows.Library</ID>
        <Version>6.1.7221.0</Version>
        <PublicKeyToken>31bf3856ad364e35</PublicKeyToken>
      </Reference>
<Reference Alias="MP1">
<ID>TaskMP1</ID>
<Version>1.0.0.0</Version>
<PublicKeyToken>0823A712C344907</PublicKeyToken>
      </Reference>

    </References>
  </Manifest>
<Presentation>
    <ConsoleTasks>
      <ConsoleTask ID="Task.LocalCalc" Accessibility="Internal" Enabled="true" Target="System!System.Entity" RequireOutput="true" Category="MonitoringObject">
        <Application>%systemroot%\system32\calc.exe</Application>
        <WorkingDirectory />
      </ConsoleTask>
    </ConsoleTasks>
  </Presentation>
  <LanguagePacks>
    <LanguagePack ID="FRA" IsDefault="false">
      <DisplayStrings>
        <DisplayString ElementID="MP_ExempleTask">
          <Name>MP Exemple Task</Name>
        </DisplayString>
      </DisplayStrings>
    </LanguagePack>
    <LanguagePack ID="ENU" IsDefault="true">
      <DisplayStrings>
        <DisplayString ElementID="Task.LocalCalc">
          <Name>Ouvrir Calculatrice</Name>
          <Description />
        </DisplayString>
        <DisplayString ElementID="MP_ExempleTask">
          <Name>MP Exemple Task</Name>
        </DisplayString>
      </DisplayStrings>
    </LanguagePack>
  </LanguagePacks>
</ManagementPack>

Comme vous pouvez le voir dans la partie surlignée, le MP2 hérite du MP1.

Nous avons donc désormais un MP1.mp (MP1 scellé) et un MP2.xml, qu’il ne reste plus qu’à importer dans la console SCOM l’un après l’autre : les tâches stockées dans le MP1 et appelées dans le MP2 apparaissent bien.

Il sera par la suite possible d’appeler de la même façon les tâches définies dans le MP1 dans autant de management packs « enfants » que nécessaire.