-1

I'm making an "Advanced Virtual Assistant" by using Python and I want to be able to run any app on the PC with just entering its name. Something likes:

i = input("What App Do You Want To Open?:  ")
d = getDirectory(i)
os.startfile(d)

Now I can set this up manually for some apps by getting their directory but it won't be for every app so its not what I need. Is there any easy way to do this?

Samuel Chen
  • 2,124
  • 14
  • 9
Ultra
  • 21
  • 2
  • You will either need to pull the registry key at `HKEY_LOCAL_MACHINE\Software\Microsoft\Windows\CurrentVersion\Uninstall`, or use the the win32 module to pull the list of `Win32_Product` classes https://learn.microsoft.com/en-us/previous-versions/windows/desktop/legacy/aa394378(v=vs.85)?redirectedfrom=MSDN – James May 28 '20 at 12:46
  • can you give me an example on how to use the registry key for this? – Ultra May 28 '20 at 12:54

4 Answers4

0

There is no easy way, but you could use something like winapps which will get you the install directory of the program if it exists. However, the hard part is knowing which file will execute the program.

You could use wmi to fetch the location by passing in the info from winapps; similar to this this answer but that may be out of date so have a look through the /docs/.

Lucan
  • 2,907
  • 2
  • 16
  • 30
  • I think WMI might work. I'll test it out. Can I get some sample code? – Ultra May 28 '20 at 13:02
  • I linked to another answer which has a sample, the documentation also has plenty of samples – Lucan May 28 '20 at 13:24
  • Can you please read what I posted: https://stackoverflow.com/questions/62064645/is-there-a-way-to-open-an-app-just-by-its-name-in-python/62091922#62091922 – Ultra May 29 '20 at 17:53
0

From Lucan's answer, I got this code:

import wmi
w = wmi.WMI()
for p in w.Win32_Product():
    if 'Box, Inc.' == p.Vendor and p.Caption and 'Box Sync' in p.Caption:
        print 'Installed {}'.format(p.Version)

Sorry but I couldn't figure it out, Where exactly does the app name go in this?

Ultra
  • 21
  • 2
0

There are many good tools to do this already.

Here is an common solution you may try implement it:

  • Scan or record apps on your PC and store records in database or formated file. (e.g. registry / program files / other folders )
  • Map app name, description, caption or etc to the app executable path.(read executable information with wmi or other way as the other answers described.)
  • Try find the entered text in the fields.
  • (if you want nature language matching, that's another story.)
  • Use Python subprocess or other function/lib to run the executable of the record you just found.
Samuel Chen
  • 2,124
  • 14
  • 9
  • I would do that, but as I said, I am building a virtual assistant, one capable of operating at any device. Storing the data might work for me, but it won't work as well on other devices – Ultra Jun 02 '20 at 17:22
  • yes, you are right. just wanted to provider a common idea. – Samuel Chen Jun 03 '20 at 16:28
0

I've written the below which uses winapps as suggested in my previous answer. This implementation has many limitations, such as it only works for programs installed for all users. However, you could alter this code to use another way of getting the install location and use getPossibleExePaths to get the executables. This answer gives some alternative ways which may be better than winapps.

import os
import winapps
import subprocess

def getPossibleExePaths(appPath):
    if not appPath:
        raise Exception("App Path cannot be None")
    pattern = appPath + ":*exe"
    try:
        returned = subprocess.check_output(['where', pattern]).decode('utf-8')
        listOfPaths = filter(None, returned.split(os.linesep))
        return [i.strip() for i in list(listOfPaths)]
    except subprocess.CalledProcessError as e:
        raise Exception(f"Error getting path for '{appPath}'")

def getAppPath(appName):
    for app in winapps.search_installed(appName):
        installPath = str(app.install_location)
        if installPath and installPath != "None":
            return installPath
    return None

if __name__ == '__main__':
    print(getPossibleExePaths(getAppPath('Chrome')))

This code utilises Window's where command so this will not work cross-platform.

However, please note that getPossibleExePaths will return a list of executable paths and not necessarily the executable that will launch the process. You'll need to figure out how your program will deal with that, there's no easy way to separate out an uninstaller.exe from launchApp.exe. You could, of course, match up the uninstall location that winapps provides and exclude it from the returned list but that doesn't solve the issue that it might not be the launch executable.

I hope that helps you

Lucan
  • 2,907
  • 2
  • 16
  • 30
  • This works for the most part, and perfectly opens up brave and chrome with just their name. For some reason, its not compatible with all apps as my other applications like discord, fortnite fail to run through this. – Ultra Jun 01 '20 at 05:59
  • As I said, it'll only work for apps installed for all users; that's just a limitation of winapps. You don't have to use winapps though, you can modify it to use your own function for getting the install locations. – Lucan Jun 01 '20 at 09:02