JanezKranjski
JanezKranjski

Reputation: 225

Get WinWord version from Python program

in one simple Python program for testing users environment, I should also get version of installed Word (example: WinWord 16, 64-bit). Any idea how to do that? I'm sure, that different GUIDs should exist, but where can I find them :-)

**** edit

I checked both suggestions, but it isn't enough. I have to get an information if Word is 32- or 64-bit. Until now, I have checked location of "winword.exe". For example: 1. location for 64-bit Office 15 c:\program files\microsoft office\office15\winword.exe 2. location for 32-bit Office 15 c:\program files (x86)\microsoft office\office15\winword.exe

I'm sure that M$ has list of GUIDs (used in registry) for latest versions of Word. But I can't find the list :-) With suggested solutions, I can't check 32- or 64- technology.

Upvotes: 3

Views: 1261

Answers (2)

Neil
Neil

Reputation: 14313

Searching shorcuts with architecture detection (32-bit or 64-bit)

I figured the additional information would be useful, but you can reduce it to just 32-bit and 64-bit.

import subprocess, os, struct

def getWordVersion():
    directory = "C:\\ProgramData\\Microsoft\\Windows\\Start Menu\\Programs"
    wordFile = ""
    wordVersion = ""

    def recursiveSearch(directory):
        for root, dirs, filenames in os.walk(directory):
            for dire in dirs:
                result = recursiveSearch(root + "\\" + dire)
                if result:
                    return result
            for filename in filenames:
                if filename.endswith(".lnk") and filename.startswith("Word "):
                    wordFile = root + "\\" + filename
                    wordVersion = filename[:-4]
                    return wordFile, wordVersion
        return False

    wordFile, wordVersion = recursiveSearch(directory)

    lnkTarget = subprocess.check_output(["C:\\WINDOWS\\system32\\WindowsPowerShell\\v1.0\\powershell.exe",
                      "(New-Object -ComObject WScript.Shell).CreateShortcut('" + wordFile + "').TargetPath"],shell=True)
    locationOfLnk = lnkTarget.strip()

    IMAGE_FILE_MACHINE_I386=332
    IMAGE_FILE_MACHINE_IA64=512
    IMAGE_FILE_MACHINE_AMD64=34404
    f=open(locationOfLnk, "rb")

    f.seek(60)
    s=f.read(4)
    header_offset=struct.unpack("<L", s)[0]
    f.seek(header_offset+4)
    s=f.read(2)
    machine=struct.unpack("<H", s)[0]
    architecture = ""

    if machine==IMAGE_FILE_MACHINE_I386:
        architecture = "IA-32 (32-bit x86)"
    elif machine==IMAGE_FILE_MACHINE_IA64:
        architecture = "IA-64 (Itanium)"
    elif machine==IMAGE_FILE_MACHINE_AMD64:
        architecture = "AMD64 (64-bit x86)"
    else:
        architecture = "Unknown architecture"

    f.close()
    return wordVersion + " "  + architecture

print(getWordVersion())

Registry Method

A method is to loop through all registry keys under Office and find the most recent one. Unfortunately, Microsoft decided it was a great idea to change the install directory in nearly every version. So, if you want to compile a complete list of all install locations, that'd work to (unless they installed it at a custom location).

Note: This is Python 3 code, if you need Python 2, then change winreg to _winreg.

import winreg

def getMicrosoftWordVersion():
    key = winreg.OpenKey(winreg.HKEY_LOCAL_MACHINE, "SOFTWARE\\Microsoft\\Office", 0, winreg.KEY_READ)
    versionNum = 0
    i = 0
    while True:
        try:
            subkey = winreg.EnumKey(key, i)
            i+=1
            if versionNum < float(subkey):
                versionNum = float(subkey)
        except: #relies on error handling WindowsError as e as well as type conversion when we run out of numbers
            break
    return versionNum


print(getMicrosoftWordVersion())

Upvotes: 2

lospejos
lospejos

Reputation: 1986

Another way is using OLE/ActiveX/COM technology. This is a some kind of high-level version of provided "registry method". Assuming you're on Windows machine since this will not work on Linux in most cases:

#!/usr/bin/env python3
from win32com.client.dynamic import Dispatch

word = Dispatch('Word.Application')
print (word)
word_version = word.version
print (word_version)
  1. Create virtualenv: $ python -m venv ve
  2. Activate virtualenv: $ ve\Scripts\activate.bat
  3. Install pypiwin32: (ve)$ pip install pypiwin32
  4. Execute: (ve)$ python detect_msword_version.py

On my Windows machine output was:

Microsoft Word

16.0

Upvotes: 0

Related Questions