【问题标题】:How to programmatically distinguish Excel 2019 from 2016?如何以编程方式区分 Excel 2019 和 2016?
【发布时间】:2020-06-27 00:19:00
【问题描述】:

我维护了一个诊断程序,它以编程方式确定 MS Office 应用程序的版本,包括 Excel 和 Word。它已在 MS Office 版本 2003、2007、2010、2013 和 2016 上正常工作。但现在我发现它错误地将 MS Office 2019 应用程序报告为 MS Office 2016。

八年前,M. A. Hanin 发布了一个类似的问题:

Identifying Excel version programmatically

mathieu 的回复,接受的答案,用于在注册表中识别 MS Office 与产品版本的相关数字。例如,数字 14.0 对应于 Office 2010。Doug Glancy 直接用打印 Excel 应用程序对象的版本属性的 VB 代码解决了这个问题:

https://docs.microsoft.com/en-us/office/vba/api/excel.application.version

这是一个 VB 脚本,用于诊断系统安装了哪个版本的 Excel(如果有):

On Error Resume Next
Set excelApp = CreateObject("Excel.Application") 
If Err.Number <> 0 Then
    WScript.Echo "Excel is not installed"
Else
    Wscript.Echo "Excel Version: " & excelApp.Version 
End If

该诊断忠实地报告了与 2011 年的帖子一致的 MS Office 版本。从那时起,它报告 Office 2013 为 15.0,Office 2016 报告为 16.0。不过,最近我惊讶地发现它还报告了 Office 2019 的 16.0 . 那是不对的! 2016 年和 2019 年的功能集明显不同,因此不应将它们混为一谈:

https://support.office.com/en-us/article/what-s-new-in-office-2019-5077cbbe-0d94-44cc-b30e-654e37629b0c?ui=en-US&rs=en-US&ad=US

是否有其他方法可以以编程方式区分 Office 2016 和 Office 2019?

【问题讨论】:

  • 您是否尝试过只运行一项新功能而不是 CreateObject?例如。连接而不是连接?如果 Err.Number 0 则不是 Excel 2019。
  • @TylerH,我认为作为临时解决方法可以很好地执行。但是,一旦 MSO 2022 发布,这不会中断吗?
  • @Snaps-a-Lot Office 2019 将成为 Office 的最后一个独立版本。我记得当他们宣布 2019 年的存在时读过这篇文章,这听起来很可能考虑到 Office 2019 仅获得 2 年的扩展支持,而不是以前版本通常的 5 年。这意味着 Office 2016 和 Office 2019 都将在 2025 年“正式”消亡(届时 Office 365 将存在 14 年)。如果微软改变主意并发布 Office 2022(这是一个很大的假设),它不太可能仍被标记为主要版本 16.0。

标签: excel ms-word ms-office


【解决方案1】:

解决方法是从 MS Office 客户端软件许可证管理工具 OSPP.VBS 的输出中解析版本号,使用 /dstatus 选项运行。下面是一个演示解决方法的示例 CMD 脚本:

:: GetOfficeVer.cmd - Print the version of a licensed MS Office package.
::   Prerequisite:
::      Copy this cmd script to a folder including these MS Office files:
::          * OSPP.VBS    - MS Office Software Protection Platform script.
::          * OSPP.HTM    - Help file for OSPP.VBS.
::          * SLERROR.XML - Data file for OSPP.VBS.
::   Syntax:
::      GetOfficeVer [ComputerName[ PackageAbbr]]
::        ComputerName    - Windows system name  (defaults to local system)
::        PackageAbbr     - Package abbreviation (list below is not exhaustive)
::          *  ProPlus    - Office Professional Plus (default)
::          *  VisioPro   - Visio Professional
::          *  InfoPath   - InfoPath Designer
::   Return Values:
::          *  If the package is licensed, print the MS Office package version
::             string using the MS Office Application.Version property format.
::          *  If the package is unlicensed, print an empty line.
@echo off
setlocal ENABLEEXTENSIONS ENABLEDELAYEDEXPANSION
if %2_==_ (set MSO_PKG=ProPlus) else (set MSO_PKG=%2)
set "MSO_PKG_LIC=cscript "%~dp0\OSPP.VBS" /dstatus %1 | findstr /R /C:"^LICENSE NAME:.*%MSO_PKG%""
for /f "tokens=1-4 delims=, " %%G in ('!MSO_PKG_LIC!') do (set MSO_VER=%%J)
if %MSO_VER%_==_ (echo.) else ( echo %MSO_VER%.0)
endlocal

使用 OSPP.VBS 的提示:

  • 执行可能需要几秒钟时间。
  • 它包含在 Application.Path 属性中存储的文件夹中。
  • 它不需要将 MS Office 安装到运行它的系统中。
  • 为此目的,它不需要以提升的方式运行。
  • 如果目标系统需要重新启动,它将失败。
  • 与所有三个版本相比,具有 2013、2016 和 2019 的版本均有效。

【讨论】:

    【解决方案2】:

    是的,v16 可以是 2016 或 2019

    这适用于我的版本。

    :GetOfficeVer
    set vbs="%temp%\_.vbs"
    if exist %vbs% del /f /q %vbs%
        >%vbs% @echo off
        >>%vbs% echo Option Explicit ' Enforce variable declaration
        >>%vbs% echo Dim oShell
        >>%vbs% echo Dim lOfficeVersion
        >>%vbs% echo Set oShell = CreateObject("WScript.Shell")
        >>%vbs% echo On Error Resume Next
        >>%vbs% echo lOfficeVersion = GetOfficeVersionNumber() 
        >>%vbs% echo MsgBox "OfficeVersion = " ^& lOfficeVersion
        >>%vbs% echo     Function GetOfficeVersionNumber()
        >>%vbs% echo         GetOfficeVersionNumber = "" 
        >>%vbs% echo         Dim sTempValue
        >>%vbs% echo         sTempValue = oShell.RegRead("HKCR\Excel.Application\CurVer\")
        >>%vbs% echo         If Len(sTempValue) ^> 2 Then GetOfficeVersionNumber = Replace(Right(sTempValue, 2), ^".^", ^"^")
        >>%vbs% echo     End Function   
    cscript //nologo %vbs%
    pause
    if exist %vbs% del /f /q %vbs%
    endlocal
    goto :EOF
    

    【讨论】:

    • 对“此处文档”技术的赞誉。但是,在具有 MSO 2019 的系统上,它不幸返回“16”。 :-(
    【解决方案3】:

    为了扩展已经给出的答案,很遗憾,OSPP.VBS 似乎是获取区分 Office 2016、2019 和 365 所需信息的最明智的方式。

    不执行cscript OSPP.VBS /dstatus,可以通过自己实现OSPP.VBS 使用的WMI 查询来获得相同的信息(此处为C#):

    // Implementation is based on the OSPP.VBS file in the Office directory,
    // when it executes the /dstatus command...
    // result examples:
    // - Office 16, Office16StandardVL_MAK edition
    // - Office 19, Office19Standard2019VL_KMS_Client_AE edition
    // - Office 16, Office16O365ProPlusR_Subscription1 edition
    // - Office 15, OfficeStandardVL_MAK edition
    
    // This constant is apparently the same for all Office versions:
    const string officeAppId = "0ff1ce15-a989-479d-af46-f275c6370663";
    
    // Note: OSPP.VBS uses == instead of <= but it seems wrong...
    string productClass;
    if (Environment.OSVersion.Version <= new Version(6, 1)) // Windows 7 or below
        productClass = "OfficeSoftwareProtectionProduct";
    else
        productClass = "SoftwareLicensingProduct";
    
    // Get the product name for all Office products having a product key:
    var query = $"SELECT Name FROM {productClass} where "
    + $"ApplicationID=\"{officeAppId}\" AND PartialProductKey <> NULL AND PartialProductKey <> \"\"";
    
    using (var searcher = new System.Management.ManagementObjectSearcher(query))
    {
        var result = new List<string>();
        foreach (var instance in searcher.Get())
        {
            result.Add(instance.Properties["Name"].Value?.ToString() ?? "Null");
        }
        
        // result now contains a list of license names with the same format as `cscript OSPP.VBS /dstatus`
    }
    

    【讨论】:

      【解决方案4】:

      您可以尝试解析 excelApp.Path 以找出安装路径。 如果新办公室安装在 C:* \Office 19\Excel.exe

      中,这将起作用

      【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2019-03-24
      • 2010-10-30
      • 1970-01-01
      • 1970-01-01
      • 2021-04-25
      • 2018-10-11
      • 2010-09-28
      • 1970-01-01
      相关资源
      最近更新 更多