How to enumerate the installed StoreApps and their ID in Windows 8 and 10

被刻印的时光 ゝ 提交于 2019-12-01 10:42:59
Elmue

Incredible that nobody has an idea! This shows how Microsoft makes us life hard. Such a universal task like enumerating the installed StoreApps with their AppUserModelId requires a cientific research department.

I finally came to a solution that works perfectly on Windows 8 and Windows 10. But a lot of code is required.

It seems that Windows does not hold the Application ID's in memory and there is no API to determine them directly. I studied all header files in the Windows 10 SDK and could not find a corresponding interface useful for that task.

But I found out how to get them. I continue after the 6 steps in my question:

  1. call IPackage->get_InstalledLocation() which returns an IStorageFolder.
  2. QueryInterface for IStorageItem
  3. call IStorageItem->get_Path()

Now you have the path were the App is installed. Windows 10 uses two base folders:

  • C:\Program Files\WindowsApps
  • C:\Windows\SystemApps

and several others like

  • C:\Windows\vpnplugins
  • C:\Windows\devicesflow
  • C:\Windows\MicracastView
  • C:\Windows\PrintDialog
  • C:\Windows\PrintDialog3D
  • C:\Windows\WinStore

In the returned folder path you will find a file "AppxManifest.xml". This file looks like:

<?xml version="1.0" encoding="utf-8"?>
<Package xmlns=".....">
    ......
    ......
    <Applications>
        <Application Id="microsoft.windowslive.mail" Executable="HxMail.exe" EntryPoint="Executable">
        ......
        ......
        </Application>
        <Application Id="microsoft.windowslive.calendar" Executable="HxCalendarAppImm.exe" EntryPoint="Executable">
        ......
        ......
        </Application>
    </Applications>
</Package>

And voilà, there they are. This package has two application ID's: "microsoft.windowslive.mail" and "microsoft.windowslive.calendar".

Then you take the package's FamilyName from step 6 append an "!" and append this ID and you are done.

This package can be started with IApplicationActivationManager->ActivateApplication() using one of the AppUserModelId's:

  • "microsoft.windowscommunicationsapps_8wekyb3d8bbwe!microsoft.windowslive.calendar"
  • "microsoft.windowscommunicationsapps_8wekyb3d8bbwe!microsoft.windowslive.mail"

Use PackageManager APIs to enumerate packages and GetPackageApplicationIds to enumerate applications in a package e.g. pseudo-code

FOREACH p IN PackageManager.FindPackagesForUserWithPackageTypes(null,
PackageType_Main|PackageType_Optional)
{
    PACKAGE_INFO_REFERENCE pir
    OpenPackageInfoByFullName(p.Id.FullName, 0, &pir)
    UINT32 n=0
    GetPackageApplicationIds(pir, &n, null, null)
    BYTE* buffer = new BYTE[n]
    UINT32 count=0
    GetPackageApplicationIds(pir, &n, buffer, &count)
    ClosePackageInfo(pir)
    PCWSTR * applicationUserModelIds = reinterpret_cast<PCWSTR*>(buffer);
    FOR (i=0; i<count; ++i)
    {
        PCWSTR applicationUserModelId = applicationUserModelIds[i]
    }
    delete [] buffer
}

See GetPackageApplicationIds() on MSDN for more details including working sample code https://msdn.microsoft.com/en-us/library/windows/desktop/dn270603(v=vs.85).aspx

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!