创建和使用自定义 scheme
啊哈哈,我又出来诈尸啦! 也是又重新用起了 Typecho ,因为自己写博客程序的话完全没时间啊魂淡! 但是网站的其他部分呢,还是会用不同的语言/技术实现。
所谓的自定义 scheme ,就是自定义 URI 协议。举个例子来说,在 Steam 上购买游戏之后,就可以看到具有这样 URI 格式的链接,点击就可以启动 Steam 客户端安装游戏。
这样做的好处显而易见:如果有些事情在浏览器里无法完成,那么用客户端软件进行辅助是非常有必要的,而自定义 scheme 可能是打通浏览器和客户端软件最便捷的一条通道。Windows 、 OSX 和 Linux 都支持这种方式调用客户端软件,但是使用的方法不一样。现在只探讨 Windows 下的实现,其他平台我用到的话会更新文章的。
根据 MSDN 上的说明: Registering an Application to a URI Scheme ,为一个应用程序注册一种 URI scheme ,需要在注册表的 HKCR
键下( HKEY_CLASSES_ROOT
)写入一系列值和子键。总体来说是下面这样的结构。
HKEY_CLASSES_ROOT
alert
(Default) = "URL:scheme_name Protocol"
URL Protocol = ""
DefaultIcon
(Default) = "icon_path"
shell
open
command
(Default) = "Drive:\path\to\you\program.exe" "%1"
首先来看一下 Steam 的实现,马上就可以理解。
这样应该很容易看懂了。
如果你使用 InnoSetup 打包程序的话,实现注册自定义的 URI scheme 很简单,只需要四行代码(放在安装包编译配置文件的 [Registry]
section 里)。
Root: HKCR; Subkey: "app_name"; ValueType: string; ValueName: ""; ValueData: "URL:scheme_name protocol"; Flags:noerror deletevalue uninsdeletevalue;
Root: HKCR; Subkey: "app_name"; ValueType: string; ValueName: "URL Protocol"; ValueData: ""; Flags:noerror deletevalue uninsdeletevalue;
Root: HKCR; Subkey: "app_name\DefaultIcon"; ValueType: string; ValueName: ""; ValueData: "{app}\{#MyAppExeName}"; Flags:noerror deletevalue uninsdeletevalue;
Root: HKCR; Subkey: "app_name\Shell\Open\Command"; ValueType: string; ValueName: ""; ValueData: """{app}\{#MyAppExeName}"" ""%1"""; Flags:noerror deletevalue uninsdeletevalue;
然后在你的程序入口(接受参数的地方,对于 Python 打包的程序来说是入口文件的启动语句处使用 sys.argv
获取参数),加入对参数的解析。
Windows 下是这样的:假设要注册一个名字叫 test 的 URI scheme ,那么浏览器访问 test:
就会启动你的程序,跟在 test:
之后的字符串都会作为参数传递给你的程序;例如 test://start
相当于终端运行 "path_to_your_app.exe" "//start"
。只要解析好入口处的参数,就可以实现对应的功能了。
2014 年 11 月 21 日修正
Windows 平台下:浏览器访问 test:
就会启动你的程序,包括 scheme 在内的所有字符串将被当作参数传递给你的程序。例如 test://start
相当于终端运行 "path_to_your_app.exe" "test://start"
。在程序入口处解析好参数就可以实现对应的功能。