Vérifier si un service Windows existe et supprimer dans PowerShell

J’écris actuellement un script de déploiement qui installe un certain nombre de services Windows.

Les noms de services sont versionnés, donc je souhaite supprimer la version de service Windows antérieure dans le cadre des installations du nouveau service.

Comment puis-je mieux faire cela dans PowerShell?

Vous pouvez utiliser WMI ou d’autres outils pour cela, car il n’y a pas d’applet de commande Remove-Service jusqu’à Powershell 6.0 ( voir doc Remove-Service).

Par exemple:

 $service = Get-WmiObject -Class Win32_Service -Filter "Name='servicename'" $service.delete() 

Ou avec l’outil sc.exe :

 sc.exe delete ServiceName 

Enfin, si vous avez access à PowerShell 6.0:

 Remove-Service -Name ServiceName 

Il n’y a pas de mal à utiliser le bon outil pour le travail, je trouve que courir (de Powershell)

 sc.exe \\server delete "MyService" 

la méthode la plus fiable qui ne comporte pas beaucoup de dépendances.

Si vous voulez simplement vérifier l’existence du service:

 if (Get-Service "My Service" -ErrorAction SilentlyContinue) { "service exists" } 

J’ai utilisé la solution “-ErrorAction SilentlyContinue”, mais j’ai ensuite rencontré le problème qu’il laissait un ErrorRecord derrière. Donc, voici une autre solution pour vérifier si le service existe en utilisant “Get-Service”.

 # Determines if a Service exists with a name as defined in $ServiceName. # Returns a boolean $True or $False. Function ServiceExists([ssortingng] $ServiceName) { [bool] $Return = $False # If you use just "Get-Service $ServiceName", it will return an error if # the service didn't exist. Trick Get-Service to return an array of # Services, but only if the name exactly matches the $ServiceName. # This way you can test if the array is emply. if ( Get-Service "$ServiceName*" -Include $ServiceName ) { $Return = $True } Return $Return } [bool] $thisServiceExists = ServiceExists "A Service Name" $thisServiceExists 

Mais ravikanth a la meilleure solution puisque Get-WmiObject ne génère pas d’erreur si le service n’existe pas. J’ai donc décidé d’utiliser:

 Function ServiceExists([ssortingng] $ServiceName) { [bool] $Return = $False if ( Get-WmiObject -Class Win32_Service -Filter "Name='$ServiceName'" ) { $Return = $True } Return $Return } 

Donc, pour offrir une solution plus complète:

 # Deletes a Service with a name as defined in $ServiceName. # Returns a boolean $True or $False. $True if the Service didn't exist or was # successfully deleted after execution. Function DeleteService([ssortingng] $ServiceName) { [bool] $Return = $False $Service = Get-WmiObject -Class Win32_Service -Filter "Name='$ServiceName'" if ( $Service ) { $Service.Delete() if ( -Not ( ServiceExists $ServiceName ) ) { $Return = $True } } else { $Return = $True } Return $Return } 

Les versions plus récentes de PS ont Remove-WmiObject. Attention au silence échoue pour $ service.delete () …

 PS D:\> $s3=Get-WmiObject -Class Win32_Service -Filter "Name='TSATSvrSvc03'" PS D:\> $s3.delete() ... ReturnValue : 2 ... PS D:\> $? True PS D:\> $LASTEXITCODE 0 PS D:\> $result=$s3.delete() PS D:\> $result.ReturnValue 2 PS D:\> Remove-WmiObject -InputObject $s3 Remove-WmiObject : Access denied At line:1 char:1 + Remove-WmiObject -InputObject $s3 + ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + CategoryInfo : InvalidOperation: (:) [Remove-WmiObject], ManagementException + FullyQualifiedErrorId : RemoveWMIManagementException,Microsoft.PowerShell.Commands.RemoveWmiObject PS D:\> 

Pour ma situation, je devais être “en tant qu’administrateur”

En combinant les réponses de Dmisorting & dcx, j’ai fait ceci:

 function Confirm-WindowsServiceExists($name) { if (Get-Service $name -ErrorAction SilentlyContinue) { return $true } return $false } function Remove-WindowsServiceIfItExists($name) { $exists = Confirm-WindowsServiceExists $name if ($exists) { sc.exe \\server delete $name } } 

On pourrait utiliser Where-Object

if ((Get-Service | Where-Object {$_.Name -eq $serviceName}).length -eq 1) { "Service Exists" }

Pour vérifier si un service Windows nommé MySuperServiceVersion1 existe, même si vous n’êtes pas certain de son nom exact, vous pouvez utiliser un caractère générique, en utilisant une sous-chaîne comme celle-ci:

  if (Get-Service -Name "*SuperService*" -ErrorAction SilentlyContinue) { # do something } 

Pour PC unique:

 if (Get-Service "service_name" -ErrorAction 'SilentlyContinue'){(Get-WmiObject -Class Win32_Service -filter "Name='service_name'").delete()} else{write-host "No service found."} 

Macro pour la liste des PC:

 $name = "service_name" $list = get-content list.txt foreach ($server in $list) { if (Get-Service "service_name" -computername $server -ErrorAction 'SilentlyContinue'){ (Get-WmiObject -Class Win32_Service -filter "Name='service_name'" -ComputerName $server).delete()} else{write-host "No service $name found on $server."} } 

Pour supprimer plusieurs services dans Powershell 5.0, la suppression du service n’existe pas dans cette version

Exécutez la commande ci-dessous

 Get-Service -Displayname "*ServiceName*" | ForEach-object{ cmd /c sc delete $_.Name} 

Adapté pour prendre une liste d’entrée de serveurs, spécifier un nom d’hôte et donner des résultats utiles

  $name = "" $servers = Get-content servers.txt function Confirm-WindowsServiceExists($name) { if (Get-Service -Name $name -Computername $server -ErrorAction Continue) { Write-Host "$name Exists on $server" return $true } Write-Host "$name does not exist on $server" return $false } function Remove-WindowsServiceIfItExists($name) { $exists = Confirm-WindowsServiceExists $name if ($exists) { Write-host "Removing Service $name from $server" sc.exe \\$server delete $name } } ForEach ($server in $servers) {Remove-WindowsServiceIfItExists($name)} 

PowerShell Core ( v6 + ) dispose désormais d’une applet de commande Remove-Service .

Je ne suis pas au courant des projets de portage vers Windows PowerShell, où il n’est pas disponible à partir de la v5.1.

Exemple:

 # PowerShell *Core* only (v6+) Remove-Service someservice 

Notez que l’invocation échoue si le service n’existe pas, alors pour le supprimer uniquement s’il existe, vous pouvez le faire:

 # PowerShell *Core* only (v6+) $name = 'someservice' if (Get-Service $name -ErrorAction Ignore) { Remove-Service $name } 

Windows Powershell 6 aura l’applet de commande Remove-Service . A partir de maintenant, la version de Github montre PS v6 beta-9

Source: https://docs.microsoft.com/en-us/powershell/module/microsoft.powershell.management/remove-service?view=powershell-6

  • Pour les versions de PowerShell antérieures à la v6, vous pouvez le faire:

     Stop-Service 'YourServiceName'; Get-CimInstance -ClassName Win32_Service -Filter "Name='YourServiceName'" | Remove-CimInstance 
  • Pour v6 +, vous pouvez utiliser l’applet de commande Remove-Service .

Observez qu’à partir de Windows PowerShell 3.0, l’applet de commande Get-WmiObject a été remplacée par Get-CimInstance.