启动已注册的mime助手应用程序

时间:2020-03-06 14:45:28  来源:igfitidea点击:

我曾经能够通过在Windows注册表中注册给定的mime类型来启动本地安装的帮助程序。这使我能够允许用户单击指向我们内部浏览器应用程序当前安装的链接一次。在Internet Explorer 5(大多数情况下)和Firefox中,此方法运行良好,但现在在Internet Explorer 7中不起作用。

传递给我的shell / open / command的文件名不是下载的安装软件包的完整物理路径。我通过IE处理的路径参数是

"C:\Document and Settings\chq-tomc\Local Settings\Temporary Internet Files\
  EIPortal_DEV_2_0_5_4[1].expd"

不幸的是,在调用FileExists()或者尝试创建TFileStream对象时,该解析无法解析为物理文件。

物理路径缺少" Content.IE5 \ ALBKHO3Q"的临时Internet文件的Internet Explorer隐藏缓存子目录,其绝对路径表示为

"C:\Document and Settings\chq-tomc\Local Settings\Temporary Internet Files\ 
  Content.IE5\ALBKHO3Q\EIPortal_DEV_2_0_5_4[1].expd"

是的,子目录是由IE随机生成的,只要IE将其完整路径传递给我的助手应用程序(不幸的是它没有这样做),就不必担心。

无需安装mime helper应用程序。它由全球登录脚本为全球所有10,000多个用户安装/更新。仅当用户单击内部网页并带有指向我们桌面浏览器应用程序安装的链接时,才会调用mime帮助器。该安装以MIME类型的" application / x-expeditors"提供。 " .expd" /" application / x-expeditors" mime类型的注册看起来像这样。

[HKEY_LOCAL_MACHINE\SOFTWARE\Classes\.expd] 
@="ExpeditorsInstaller"
"Content Type"="application/x-expeditors"

[HKEY_LOCAL_MACHINE\SOFTWARE\Classes\ExpeditorsInstaller]
"EditFlags"=hex:00,00,01,00

[HKEY_LOCAL_MACHINE\SOFTWARE\Classes\ExpeditorsInstaller\shell]

[HKEY_LOCAL_MACHINE\SOFTWARE\Classes\ExpeditorsInstaller\shell\open]
@=""

[HKEY_LOCAL_MACHINE\SOFTWARE\Classes\ExpeditorsInstaller\shell\open\command]
@="\"C:\projects\desktop2\WebInstaller\WebInstaller.exe\" \"%1\""

[HKEY_LOCAL_MACHINE\SOFTWARE\Classes\MIME\Database\Content Type\application/x-expeditors]
"Extension"=".expd"

我曾考虑枚举用户的所有IE缓存条目,但我会担心要检查它们的时间,否则我可能会在寻找当前条目之前找到一个较旧的缓存条目。但是,方括号中的文件名后缀" [[n]""可能是唯一键。

我尝试了wininet方法" GetUrlCacheEntryInfo",但这需要URL,而不是IE移交的虚拟路径。

我希望有一个Shell函数,给定虚拟路径将退还物理路径。

解决方案

我相信由IE创建的子目录是随机生成的,因此我们将无法保证每次都将其命名为相同的名称,而我在注册表方法中看到的问题是,它仅在文件仍然存在时才起作用在缓存中...清空缓存将清除需要再次安装的文件。

将此助手安装到应用程序数据中会更好吗?

我不确定这一点,但也许这可能会引导我们朝正确的方向:尝试使用Wininet DLL中的URL缓存功能:FindFirstUrlCacheEntry,FindNextUrlCacheEntry,FindCloseUrlCache进行枚举,以及在找到其本地文件名与给定路径匹配的条目时我们可以使用RetrieveUrlCacheEntryFile来检索文件。

我在X-Appl浏览器中使用了类似的系统来显示WAML Web应用程序,并且它运行良好。也许我们应该看看他们如何做到这一点。

好像iexplore正在传递文件的外壳名称空间"名称",而不是文件系统名称。

我不认为有一种文档化的方式可以在命令行资源管理器中将外壳项目ID传递给自身,但是存在编组注意事项,因为外壳项目ID是(指向的)二进制数据结构,仅在单个进程中有效。

我可能会尝试做的是:
1.调用SHGetDesktopFolder,它将返回外壳名称空间的根IShellFolder对象。
2.调用IShellFolder :: ParseDisplayName将我们获得的名称转回到外壳项目ID列表中。
3.尝试使用带有SHGDN_FORPARSING标志的IShellFolder :: GetDisplayNameOF,坦率地说,感觉就像是走了一个完整的圈,回到了我们开始的地方。因为我认为该API最终负责返回"错误的"文件系统相对路径。

一些后续行动可以解决这个问题。

真正的问题是我如何使用TFileStream创建文件句柄。我改用fmOpenRead或者fmShareDenyWrite打开,这解决了原来是文件锁定的问题。

srcFile := TFileStream.Create(physicalFilename, fmOpenRead or fmShareDenyWrite);