简体   繁体   English

获取MS Office列表

[英]Get a List of MS Office

Ok, I am trying to get a list off all Office versions and how many of each. 好的,我正在尝试列出所有Office版本以及每个版本的数量。 We are migrating to Windows 10 and I am trying to talk him into upgrading office to 2016. We have Office as old as 2010. I need a list of how many of each version we have. 我们正在迁移到Windows 10,我正试图说服他将Office升级到2016年。我们的Office早于2010年。我需要列出每个版本中有多少个。 Even if i can get a list of what computer has what version. 即使我可以获得什么计算机具有什么版本的列表。 I am trying not to run an audit on every computer individually, we have 200 computers. 我尝试不对每台计算机分别进行审核,因为我们有200台计算机。

I have tried several different approaches. 我尝试了几种不同的方法。

Get-ADComputer -Filter * -Property * | Select-Object Name |
 Export-CSV ADcomputerslist.csv -NoTypeInformation -Encoding UTF8

This doesnt actually save to a file 这实际上并没有保存到文件

foreach ($computer in (Get-Content "c:\computers.txt")){
  Write-Verbose "Working on $computer..." -Verbose
  Invoke-Command -ComputerName "$Computer" -ScriptBlock {
    Get-ItemProperty HKLM:\Software\Microsoft\Windows\CurrentVersion\Uninstall\O365ProPlusRetail* |
    Select-Object DisplayName, DisplayVersion, Publisher
  } | export-csv C:\results.csv -Append -NoTypeInformation
}

It's generally considered unsafe to use Get-WmiObject to check the Win32_Product class because this can unintentionally trigger repair installs on software. 通常认为使用Get-WmiObject检查Win32_Product类是不安全的,因为这可能无意间触发软件上的修复安装。 It's safer to check the registry for installed programs: 检查注册表中已安装的程序更安全:

# We need to check for both 64-bit and 32-bit software
$regPaths = "HKLM:\SOFTWARE\Wow6432node\Microsoft\Windows\CurrentVersion\Uninstall",
  "HKLM:\SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall"

# Get the name of all installed software registered in the registry with Office in the name
# (you can search for exact strings if you know them for specific versions)
$regPaths | Foreach-Object {
  ( Get-ItemProperty "${_}\*" DisplayName -EA SilentlyContinue ).DisplayName | Where-Object {
    $_ -match 'office'
  }
}

The way this works is that for both registry paths, we want to get the DisplayName value every key underneath the base path from $regPaths (these are mostly going to be GUID-named keys, not much value for just identifying the software by name). 这种工作方式是,对于两个注册表路径,我们都希望从$regPaths基本路径下每个键的DisplayName值(这些键大多是GUID命名的键,仅通过名称标识软件没有太大的值) 。 We ignore errors since they will clutter the output and for this operation it's expected that some keys may not have a DisplayName property. 我们忽略错误,因为它们会使输出混乱,并且对于此操作,预期某些键可能没有DisplayName属性。 We don't care about those. 我们不在乎那些。

Once we have the DisplayName enumerated for all of the subkeys, we want to filter out the ones that do not have 'Office' in the name. 枚举所有子项的DisplayName ,我们要过滤掉名称中没有“ Office”的子项。 Note that the -match operator is case-insensitive, so casing doesn't matter here. 请注意, -match运算符不区分大小写,因此此处的大小写无关紧要。 So the Where-Object clause only returns a DisplayName of it finds the string office in it. 因此, Where-Object子句仅返回一个DisplayName ,它在其中找到字符串office You can tweak this regular expression if you know exact DisplayName strings for each version of Office you support, as inherently this will return anything with Office in the name. 如果知道支持的每个Office版本的确切DisplayName字符串,则可以调整此正则表达式,因为从本质上讲,这将返回名称中带有Office任何内容。

As an alternative you could read the (default) registry value for one of the Office applications like Word and translate the version number: 或者,您可以读取其中一个Office应用程序(如Word (default)(default)注册表值并转换版本号:

foreach ($computer in (Get-Content "c:\computers.txt")){
  Write-Verbose "Working on computer '$computer'..." -Verbose

  Invoke-Command -ComputerName $computer -ScriptBlock {
    (Get-ItemProperty -Path "Registry::HKEY_CLASSES_ROOT\Word.Application\CurVer").'(default)' | ForEach-Object {
        [PsCustomObject] @{
            'Computer' = $computer
            'OfficeVersion' = 
                    switch ([int]($_ -split '\.')[-1]) {
                            16 {'MS Office 2016 OR MS Office 2019 or MS Office 365'; break}
                            15 {'MS Office 2013'; break}
                            14 {'MS Office 2010'; break}
                            12 {'MS Office 2007'; break}
                            11 {'MS Office 2003'}
                        }
        }
    }
  } 
}

Output (something like): 输出(类似):

 Computer OfficeVersion -------- ------------- PC_01 MS Office 2013 PC_02 MS Office 2010 

Unfortunately, Office 2019 and Office 2016 are no longer differentiated by a different version number in this registry value.. 不幸的是,在此注册表值中,Office 2019和Office 2016不再由其他版本号区分。

I would do it like this :- 我会这样:-

First start the WinRM serviice 首先启动WinRM服务

Get-Service -Name WinRM  -ComputerName machinename | Start-service

Then once we have that we can query WinRM for all the installed applications. 然后,一旦有了,我们就可以向WinRM查询所有已安装的应用程序。

Get-CimInstance -ComputerName machinename -ClassName win32_product | Select-Object PSComputerName, Name, PackageName, InstallDate 

Then its good practice disable WinRM when you have finished 然后,它的良好做法是在完成后禁用WinRM

Get-Service -Name WinRM  -ComputerName df-ps-sitpc17 | Stop-service

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM