2017-04-13 86 views
2

全部。Powershell:查找已安装的防病毒软件,过滤掉Windows Defender

我有一个PowerShell脚本,它将检测安装在Windows中的防病毒软件(它实际上很常见)。问题是,我想要它过滤Windows Defender,尤其是在Windows 8,8.1和10自带安装的情况下。我希望我的脚本能够指示Windows Defender是否仅显示防病毒软件,如果是,则显示不同的输出。

这里是我迄今为止...

function Get-AntivirusName { 
[cmdletBinding()]  
param ( 
[string]$ComputerName = "$env:computername" , 
$Credential 
) 
    BEGIN 
     { 
      $wmiQuery = "SELECT * FROM AntiVirusProduct" 
     } 
    PROCESS 
     {  
      $AntivirusProduct = Get-WmiObject -Namespace "root\SecurityCenter2" -Query $wmiQuery @psboundparameters   
      $AntivirusNames = $AntivirusProduct.displayName  
      if ($AntivirusNames -eq "") { 
       Write-host "Anti-Virus is NOT installed!" 
      } 
      elseif ($AntivirusNames -eq "Windows Defender") { 
       Write-host "ONLY Windows Defender is installed!" 
      } 
      else { 
       Write-host "Anti-Virus is installed (" + $AntivirusNames + ")." 
      } 

     } 
    END { 
     } 
} 

Get-AntivirusName 

结果是,不管所安装的其他杀毒软件的应用程序,它不断告诉我只安装了Windows Defender的。有人能指出我错过了什么吗?

非常感谢!

回答

1

我的猜测是它检查elseif语句中数组的每个元素,所以即使有多个结果也是如此。你可以添加一个条件,即只有一个结果如下:

elseif ($AntivirusNames -eq "Windows Defender" -and $AntivirusNames.count -eq 1) { 
       Write-host "ONLY Windows Defender is installed!" 
      } 
2

我会宣布$AntivirusNames是当你将它,然后在结果使用一个开关循环数组。

function Get-AntivirusName { 
[cmdletBinding()]  
param ( 
[string]$ComputerName = "$env:computername" , 
$Credential 
) 
    BEGIN 
     { 
      $wmiQuery = "SELECT * FROM AntiVirusProduct" 
     } 
    PROCESS 
     {  
      $AntivirusProduct = Get-WmiObject -Namespace "root\SecurityCenter2" -Query $wmiQuery @psboundparameters   
      [array]$AntivirusNames = $AntivirusProduct.displayName  
      Switch($AntivirusNames) { 
       {$AntivirusNames.Count -eq 0}{"Anti-Virus is NOT installed!";Continue} 
       {$AntivirusNames.Count -eq 1 -and $_ -eq "Windows Defender"} {"ONLY Windows Defender is installed!";Continue} 
       {$_ -ne "Windows Defender"} {"Anti-Virus is installed ($_)."} 
      } 
} 
    END { 
     } 
} 
Get-AntivirusName 

因此,切换...如果没有结果,则声明没有安装AV。如果有1个结果,并且是Windows Defender,则声明该结果。否则,如果当前结果不是Windows Defender输出实际AV的内容。

在一个侧面说明,因为你没有允许在你的参数任何一个数组,你可以只跳过BEGININGPROCESS和东西所有的代码到END,此时你可以跳过宣布所有这些块的。

function Get-AntivirusName { 
[cmdletBinding()]  
param ( 
[string]$ComputerName = "$env:computername" , 
$Credential 
) 
    $wmiQuery = "SELECT * FROM AntiVirusProduct" 
    $AntivirusProduct = Get-WmiObject -Namespace "root\SecurityCenter2" -Query $wmiQuery @psboundparameters   
    [array]$AntivirusNames = $AntivirusProduct.displayName  
    Switch($AntivirusNames) { 
     {$AntivirusNames.Count -eq 0}{"Anti-Virus is NOT installed!";Continue} 
     {$AntivirusNames.Count -eq 1 -and $_ -eq "Windows Defender"} {Write-host "ONLY Windows Defender is installed!";Continue} 
     {$_ -ne "Windows Defender"} {"Anti-Virus is installed ($_)."} 
    } 
} 
Get-AntivirusName 
2

的主要问题是:

$AntivirusProduct = Get-WmiObject ... 
$AntivirusNames -eq "Windows Defender" 

Get-WmiObject返回单个项目,$AntivirusNames变成一个字符串,-eq测试它的文字字符串相匹配。

Get-WmiObject返回多个项目时,$AntivirusNames成为数组,并且-eq开始作为过滤器,过滤出与文字字符串匹配的项目。即,如果该数组包含“Windows Defender”,则它执行该操作。