Vous avez franchi le pas de la gestion de vos PC en mode Full Cloud sur AZURE. Fini les serveurs On-Prem et l’Active Directory local.

Bienvenu dans le monde moderne !

Seulement voilà, vous devez tout de même pouvoir imprimer vos documents sur l’imprimante reseau qui trône dans votre service.

Comment faire pour que vos utilisateurs puissent avoir cette imprimante installée sur leur machine en un seul clic, voire automatiquement en arrière-plan ?

La solution importer les Pilotes et un script d’installation dans une Win32App dans Intune et utiliser le « Company Portal » (Portail d’entreprise) pour le mettre à disposition de vos utilisateurs.

Les Pilotes et le script PowerShell

PowerShell va nous aider à installer cette imprimante, mais avant tout il faut récupérer les pilotes que nous souhaitons installer sur nos machines.

Pour cela rien de plus simple, il suffit de les récupérer sur le site de l’éditeur, et d’en retirer les fichiers qui nous intéressent.

Dans notre exemple, nous allons installer une imprimante CANON Image Runner Advance C3520i

Les pilotes sont à télécharger ici.

De ces derniers seuls nous intéresse le pilote PCL destinés aux machines 64 bits

De l’exécutable téléchargé il faut récupérer les fichiers *.cat, *.inf et *.cab qui nous concernent…

…et les disposer dans un répertoire qui contiendra notre package.

C’est dans le Fichier *.INF que vous trouverez le nom du Pilote qu’il faudra renseigner dans votre script :

Passons à présent à notre Script d’installation/Désinstallation.

Ce dernier aura pour fonctions :

Et bien sûr chaque étape est enregistrée dans un fichier de LOG sur la machine (c:\windows\temp)

Il est à noter que l’utilisation du répertoire virtuel « SYSNATIVE » est indispensable pour que la commande PNPUTIL.EXE s’exécute correctement car le package s’exécutera en 32bits sur les machines 64bits

#—————————————————————————————
## PARAMETER ##
#——————————————————————————————

PARAM (
    [Parameter(Mandatory=$true)][validateset (« Install », »Uninstall »)]$Action= »Install »
)

#—————————————————————————————
## INIT ##
#—————————————————————————————

#Fichier de log.

$global:logfile = $env:SystemRoot+ »\temp »

$DriverName= « Canon Generic Plus PCL6 »

$PrinterName= « Canon C3520i Paris Siege »

$IPPort_address= « XXX.XXX.XXX.XXX »

$IPPort_Name   = « IP_ »+$IPPort_address

#—————————————————————————————
## FUNCTIONS ##
#—————————————————————————————

#region Function

#Supression des caracteres LAtins dans les chaines de caractère

Function Remove-StringLatinCharacters

{
    PARAM ([string]$String)
    [Text.Encoding]::ASCII.GetString([Text.Encoding]::GetEncoding(« Cyrillic »).GetBytes($String))
}

#Creation du fichier de log.

Function new-log

 {

   #Verifier le chemin.
   $logdir = $global:logfile # récupere le chemin où se trouve le script
   $pathr = Test-Path $logdir
   if ($pathr -ne « True ») { $rtn = New-Item -ItemType directory -Path $logdir -Force }

   #Créer le dossier de logs.

   $global:logfile = $logdir + « \ » + [string](Get-Date -UFormat « %Y%m%d ») + « -install-$($PrinterName.replace(‘ ‘,’_’)).log »

   $pathr = Test-Path $global:logfile

   if ($pathr -ne « True »)

     {

       #Créer le fichier de log.

       $rtn = New-Item -ItemType file -Path $global:logfile -Force

       #Ecrire l’évenement dans le log.

       add-log « Script » « INFO » « Creation automatique du fichier de log. »

     }

 }

#Enregistre une information dans le fichier de log.

Function add-log

 {

   [CmdletBinding()]

   PARAM (

           [Parameter(Mandatory=$true)][string] $li_source,

           [Parameter(Mandatory=$true)][string] $li_type,

           [Parameter(Mandatory=$true)][String] $li_message

         )

   #suppression des accents du message

   $li_message = Remove-StringLatinCharacters $li_message

   #Ecriture dans le fichier de log.

   Add-Content -Path $global:logfile -Value ([string](Get-Date -UFormat « %d/%m/%Y-%H:%M:%S ») +  » :  » + $li_source +  » –  » + $li_type+ » –  » + $li_message)

   #Debug.

   #Write_Debug ($li_source +  » –  » + $li_type+ » –  » + $li_message)

 }

#endregion

#—————————————————————————————
## MAIN ##
#—————————————————————————————

new-log

add-log « INIT » « INFO » « !——————————————————-! »

Switch ($Action)

{

« Install »

            {

                    add-log « Install » « INFO » « Import des Drivers: $DriverName dans le store systeme »

                    #region Import Driver

                    try

                    {

                        $pnputilresult=Invoke-Command {& cmd /c ‘C:\Windows\SysNative\pnputil.exe /add-driver x64\*.inf’}

                        add-log « Install » « INFO » « $pnputilresult »

                    }

                    catch

                    {

                        $ErrorMessage = $_.Exception.Message

                        add-log « PNPUTIL » « ERROR » « Import Driver : $ErrorMessage »

                    }

                    #endregion

                    #region Install Driver

                    try

                    {

                        if (Get-PrinterDriver -Name $DriverName -ErrorAction SilentlyContinue)

                        {

                            add-log « Driver-Check » « WARNING » « Le driver $DriverName existe deja »

                        }

                        else

                        {

                            add-log « Driver-Check » « INFO » « Le driver $DriverName n’existe pas! »

                            add-log « Install » « INFO » « Installation des Drivers: $DriverName »

                            Add-PrinterDriver -Name $DriverName -ErrorAction SilentlyContinue

                        }

                    }

                    catch

                    {

                        $ErrorMessage = $_.Exception.Message

                        add-log « ADD Printer Driver » « ERROR » « Installation des drivers : $ErrorMessage »

                    }

                    #endregion     

                    #region Printer Port creation

                    try

                    {

                        $GPP=Get-PrinterPort -Name $IPPort_Name -ErrorAction SilentlyContinue

                        if(($GPP.name -eq $IPPort_Name) -and ($GPP.printerHostAddress -eq $IPPort_address))

                        {add-log « Install » « WARNING » « Le port $IPPort_Name existe deja »}

                        if(($GPP.name -eq $IPPort_Name) -and ($GPP.printerHostAddress -ne $IPPort_address))

                        {

                            add-log « Install » « WARNING » « Le port $IPPort_Name existe deja, mais l’adresse $($GPP.printerHostAddress) ne correspond pas à $IPPort_address »

                            add-log « Install » « WARNING » « Suppression du port $IPPort_Name existant »

                            Remove-PrinterPort -Name $IPPort_Name

                            Start-Sleep 10

                            add-log « Install » « INFO » « Creation du port IP: $IPPort_Name »

                            Add-PrinterPort -Name $IPPort_Name -PrinterHostAddress $IPPort_address

                            #Add-PrinterPort -Name $IPPort_Name -PrinterHostAddress $IPPort_address -SNMP 0 -SNMPCommunity « public »

                         }

                        if(!$GPP)

                        {

                            add-log « Install » « INFO » « Creation du port IP: $IPPort_Name »

                            Add-PrinterPort -Name $IPPort_Name -PrinterHostAddress $IPPort_address

                            #Add-PrinterPort -Name $IPPort_Name -PrinterHostAddress $IPPort_address -SNMP 0 -SNMPCommunity « public »

                            Start-Sleep 10

                        }

                    }

                    catch

                    {

                        $ErrorMessage = $_.Exception.Message

                        add-log « ADD PRINTER PORT » « ERROR »  » $ErrorMessage »

                        break

                    }

                    #endregion

                    #region Add Printer

                    try

                    {

                        $GP=Get-Printer -Name $PrinterName -ErrorAction SilentlyContinue

                        if(($GP.name -eq $PrinterName) -and ($GP.PortName -eq $IPPort_Name) -and ($GP.DriverName -eq $DriverName))

                        {

                            add-log « Install » « Warning » « L’imprimante $PrinterName, sur le port $IPPort_Name, avec le driver $DriverName Existe deja »

                        }

                        else

                        {

                            if($GP)

                            {

                                add-log « Install » « Warning » « L’imprimante $PrinterName existe deja mais avec le mauvais port ou driver »

                                add-log « Install » « Warning » « Suppression de l’imprimante $($GP.name) »

                                Remove-Printer -Name $PrinterName

                                Start-Sleep 10

                            }

                            add-log « Install » « INFO » « Ajout de l’imprimante : $PrinterName »

                            Add-Printer -Name $PrinterName -PortName $IPPort_Name -DriverName $DriverName

                        }

                    }

                    catch

                    {

                        $ErrorMessage = $_.Exception.Message

                        add-log « ADD PRINTER » « ERROR »  » $ErrorMessage »

                    }

                    #endregion

                    #region Custom Printer

                    try

                    {

                        $wmiprt = Get-CimInstance win32_printer -filter « name=’$PrinterName' » -ErrorAction SilentlyContinue

                        if(!$wmiprt.DoCompleteFirst)

                        {

                            add-log « Install » « INFO » « Ajout paramètre avancé ` »Imprimer d’abord les documents dans le spouleur` » »

                            $wmiprt.DoCompleteFirst = $true

                            Set-CimInstance $wmiprt

                        }

                        else

                        {

                            add-log « Install » « Warning » « L’imprimante $PrinterName, paramètre avancé ` »Imprimer d’abord les documents dans le spouleur` » deja actif »

                        }

                    }

                    catch

                    {

                        $ErrorMessage = $_.Exception.Message

                        add-log « CUSTOM PRINTER » « ERROR »  » $ErrorMessage »

                    }

                   #endregion

            }

« Uninstall »

            {

                    add-log « Uninstall » « INFO » « suppression de l’imprimante : $PrinterName »

                    #region REMOVE Printer

                    try

                    {

                        Remove-Printer -Name $PrinterName -ErrorAction SilentlyContinue

                    }

                    catch

                    {

                        $ErrorMessage = $_.Exception.Message

                        add-log « REMOVE PRINTER » « ERROR »  » $ErrorMessage »

                    }

                    #endregion

                    add-log « Uninstall » « INFO » « suppression du port  : $IPPort_Name »

                    #region REMOVE Printer PORT

                    try

                    {

                        Remove-PrinterPort -Name $IPPort_Name -ErrorAction SilentlyContinue

                    }

                    catch

                    {

                        $ErrorMessage = $_.Exception.Message

                        add-log « REMOVE PRINTER PORT » « ERROR »  » $ErrorMessage »

                    }

                    #endregion

                    add-log « Uninstall » « INFO » « suppression du Driver  : $DriverName »

                    #region REMOVE Printer DRIVER

                    try

                    {

                        Remove-PrinterDriver -Name $DriverName -ErrorAction SilentlyContinue

                    }

                    catch

                    {

                        $ErrorMessage = $_.Exception.Message

                        add-log « REMOVE PRINTER PORT » « ERROR »  » $ErrorMessage »

                    }

                    #endregion

            }

}

add-log « Main » « INFO » « Fin de traitement! » 

Il faut maintenant enregistrer notre script dans le répertoire contenant déjà les fichiers de notre Pilote.

En lui donnant un nom explicite : install-printer.ps1

On peut aussi y ajouter une petite image qui nous servira d’icone dans notre portail d’entreprise.

Reste maintenant à créer notre package Intune.

Création du package pour Intune

Pour cela vous allez avoir besoin de télécharger l’utilitaire qui va vous permettre de transformer votre Répertoire (les sources de votre package) en un fichier exploitable par Intune. Cet utilitaire est IntuneWinAppUtil.exe que vous pourrez trouver ici.

Pour la suite il suffit d’ouvrir une invite de commande (en tant qu’administrateur si possible) et d’exécuter la commande suivante :

IntuneWinAppUtil.exe -c <Chemin complet vers votre répertoire contenant vos sources> -s <Chemin complet vers votre script ou exécutable> -o <Chemin complet vers le répertoire ou sera sauvé votre package>

Voici un exemple de commande :

IntuneWinAppUtil.exe -c C:\TEMPO\intune-pckg\Printer-IRC3520\sources -s C:\TEMPO\intune-pckg\Printer-IRC3520\sources\Install-printer.ps1 -o C:\TEMPO\intune-pckg\Printer-IRC3520

S’il existe déjà un package portant le même nom dans votre répertoire de destination, l’outil vous demandera si vous souhaitez l’écraser ou non.

Et voilà votre package est prêt.

Maintenant il faut l’importer dans Intune et configurer le déploiement.

Import du package dans Intune

Maintenant tout se passe dans votre portail Endpoint manager.

Il faut bien sûr avoir un compte disposant des droits suffisants :

Intune Adminstrator ou Global Administrator

Et suivez les étapes suivantes :


Aller dans la section Apps
Puis Windows
Cliquer sur « Add »
Sectionner le type d’application « Windows app (win32) »
et cliquer « Select »
Importer votre package en cliquant sur le lien « Select app package file »
Aller chercher votre fichier  » *.intunewin  » et Cliquer « OK »

Renseigner les informations de votre application qui apparaitront dans le portail d’entreprise et Intune.
Définir si l’application doit apparaitre dans le Company Portal
C’est aussi là que vous pourrez ajouter l’image qui symbolisera votre application dans le portail.

Renseigner les lignes de commandes pour l’installation et la désinstallation.
Install:
powershell.exe -Executionpolicy Bypass « .\Install-printer.ps1 -action Install » 
Uninstall:
powershell.exe -Executionpolicy Bypass « .\Install-printer.ps1 -action unInstall »
Définir les prérequis à l’installation.
Cela peut être l’architecture du système, la version minimum de Windows, l’espace disque, …
 Il est possible de joindre un script qui vérifiera des prérequis plus spécifiques à votre environnement.
Il est temps de définir la méthode de détection qui permettra à Intune de savoir si votre application est bien présente sur votre machine

Dans notre exemple la méthode de détection s’appuie sur la présence d’une clé de registre liée à notre Imprimante

HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\Print\Printers\Canon C3520i Paris Siege

value: blank

key exists

Il est possible de définir une liste d’applications qui doivent aussi être installées sur la machine pour le bon fonctionnement de votre application (les dépendances)

La gestion des supersédence est en preview et n’a pas encore été testée.

Cette fonction doit permettre, lors d’une évolution de l’application, de définir l’application qui devra être remplacée par votre application et gérer sa désinstallation avant d’installer votre version.When you supersede an application, you can specify which app will be updated or replaced. To update an app, disable the uninstall previous version option. To replace an app, enable the uninstall previous version option. There is a maximum of 10 updated or replaced apps, including references to other apps. For example, your app references another app. This other app references other apps, and so on. This scenario creates a graph of apps. All apps in the graph count toward the maximum value of 10. Learn more

Votre Application est presque prête.

Il faut à présent gérer les Assignations. C’est-à-dire qui aura le droit d’installer l’application via son « Company Portal », qui verra l’application automatiquement installée sur sa machine en arrière-plan et qui se verra désinstaller l’application.

Pour cela il faudra créer au préalable des groupes contenant les utilisateurs qui seront ciblés par chacune des actions

Ne reste plus qu’à valider et attendre que votre Package soit complétement chargé dans Intune.

Installation via Company Portal

Sur les machines Windows, il suffit de lancer le company portal (ou Portail d’entreprise)

Les Machine jointes à Azure et enrollées dans Intune ont automatiquement cette application installée.

Vous retrouverez votre application dans le portail et ne vous restera plus qu’à cliquer pour l’installer

Voilà votre imprimante est installée

Limitation

Il n’est pour l’instant pas possible de désinstaller une application via le Company portal, mais un userVoice a été créé pour demander à Microsoft de corriger ce manque.

Je vous invite à ajouter votre voix à ce souhait et inciter Microsoft à combler ce manque.

Si vous êtes intéressé par Intune vous pourrez également retrouver notre article « Pourquoi Intune? » traitant du même thème.