Chrome中的自定义协议处理程序

99

我如何在Chrome中设置自定义协议处理程序?例如:

myprotocol://testfile

我需要将此发送到http://example.com?query=testfile,然后将HTTP响应发送到我的扩展程序。


我认为Chrome目前不支持这一点,它给扩展提供了相对有限的API集合。 - Wladimir Palant
7个回答

93
以下方法可以将应用程序注册到URI方案中。因此,您可以在HTML代码中使用“mycustproto:”来触发本地应用程序。它适用于Google Chrome版本51.0.2704.79 m(64位)。
我主要使用这种方法来静默打印文档,而不会弹出打印对话框。结果非常好,是将外部应用程序与浏览器集成的无缝解决方案。
HTML代码(简单):
<a href="mycustproto:Hello World">Click Me</a>

HTML代码(替代方案):

<input id="DealerName" />
<button id="PrintBtn"></button>

$('#PrintBtn').on('click', function(event){
  event.preventDefault();
  window.location.href = 'mycustproto:dealer ' + $('#DealerName').val();
});

URI方案看起来像这样:

您可以在注册表中手动创建URI方案,或者运行“mycustproto.reg”文件(请参见下文)。

HKEY_CURRENT_USER\Software\Classes
   mycustproto
      (Default) = "URL:MyCustProto Protocol"
      URL Protocol = ""
      DefaultIcon
         (Default) = "myprogram.exe,1"
      shell
         open
            command
               (Default) = "C:\Program Files\MyProgram\myprogram.exe" "%1"

mycustproto.reg示例:

Windows Registry Editor Version 5.00

[HKEY_CURRENT_USER\Software\Classes\mycustproto]
"URL Protocol"="\"\""
@="\"URL:MyCustProto Protocol\""

[HKEY_CURRENT_USER\Software\Classes\mycustproto\DefaultIcon]
@="\"mycustproto.exe,1\""

[HKEY_CURRENT_USER\Software\Classes\mycustproto\shell]

[HKEY_CURRENT_USER\Software\Classes\mycustproto\shell\open]

[HKEY_CURRENT_USER\Software\Classes\mycustproto\shell\open\command]
@="\"C:\\Program Files\\MyProgram\\myprogram.exe\" \"%1\""

C#控制台应用程序 - myprogram.exe:

using System;
using System.Collections.Generic;
using System.Text;

namespace myprogram
{
  class Program
  {
    static string ProcessInput(string s)
    {
       // TODO Verify and validate the input 
       // string as appropriate for your application.
       return s;
    }

    static void Main(string[] args)
    {
      Console.WriteLine("Raw command-line: \n\t" + Environment.CommandLine);
      Console.WriteLine("\n\nArguments:\n");

      foreach (string s in args)
      {
        Console.WriteLine("\t" + ProcessInput(s));
      }

      Console.WriteLine("\nPress any key to continue...");
      Console.ReadKey();
    }
  }
}

先尝试运行程序,确保程序已放置在正确的路径中:

cmd> "C:\Program Files\MyProgram\myprogram.exe" "mycustproto:Hello World"

点击HTML页面上的链接:

您将会看到一个警告窗口第一次弹出。

enter image description here

在Chrome中重置外部协议处理程序设置:

如果您曾经在Chrome中接受过自定义协议并希望重置设置,可以执行以下操作(目前,Chrome中没有UI来更改设置):

编辑此路径下的文件“Local State”

C:\Users\Username\AppData\Local\Google\Chrome\User Data\

或者直接前往:

%USERPROFILE%\AppData\Local\Google\Chrome\User Data\

然后,搜索此字符串:protocol_handler

您将从那里看到自定义协议。

注意:在编辑文件之前,请关闭您的Google Chrome。否则,您所做的更改将被Chrome覆盖。

参考:

https://msdn.microsoft.com/en-us/library/aa767914(v=vs.85).aspx


1
@Venkat 我认为最好先指定平板电脑的名称和操作系统(例如:Surface,iPad等),看看其他人是否已经这样做了。我发布的解决方案是针对Windows的。我已经看到了OS X和Linux的类似设置。但是,我没有这些设备/环境来进行实验。你可以先在Windows上尝试一下,以了解它的基本工作原理。希望这会有所帮助。 - Jun Hsieh
3
记录一下,我在位于 %localappdata%\Google\Chrome\User Data\DefaultPreferences 文件中找到了 protocol_handler 配置选项。 - Babblo
如果我的键在注册表中找不到怎么办?从浏览器中,我要求根据该键调用应用程序?在这种情况下,我如何通知用户在注册表中找不到该键? - Akhil Nair
你提到你使用这个来打印文件,但是我在你提供的例子中没有看到任何打印功能。你有更多的文档吗? - Helpful
我不相信你的样本.reg文件是正确的:例如,当URL Protocol的值应该是空字符串而不是两个双引号时,你已经转义了引号。 - NetMage
显示剩余2条评论

55

Chrome 13 现在支持 navigator.registerProtocolHandler API。例如:

navigator.registerProtocolHandler(
    'web+custom', 'http://example.com/rph?q=%s', 'My App');

请注意,您的协议名称必须以web+开头,但对于一些常见协议(如mailto等),有少数例外。有关更多详细信息,请参见:http://updates.html5rocks.com/2011/06/Registering-a-custom-protocol-handler


6
+1 是因为协议必须以 web+ 开头,以避免出现“SECURITY_ERR: DOM Exception 18”的错误。 - Catch22
4
怎么样使用 torrent:steam: 链接?Chrome 打包应用程序是否也有此限制? - Steven Roose
1
据我所知,Chrome将这些传递给操作系统。即使使用“chrome.webNavigation”API,也从未报告“tel:”链接。 - PixnBits
这似乎在Chrome应用程序内无法工作,并且似乎无法在应用程序内重定向协议。更好的答案是下面的Gordon Williams答案。 - Karel Bílek
https://developer.mozilla.org/en-US/docs/Web/API/Navigator/registerProtocolHandler - Artistan

33

这个问题现在有些陈旧了,但是最近Chrome进行了更新(至少涉及打包应用程序)...

http://developer.chrome.com/apps/manifest/url_handlers

并且

https://github.com/GoogleChrome/chrome-extensions-samples/blob/e716678b67fd30a5876a552b9665e9f847d6d84b/apps/samples/url-handler/README.md

它允许您为URL注册处理程序(只要您拥有该URL)。不幸的是没有myprotocol://,但至少您可以使用http://myprotocol.mysite.com并在那里创建一个网页,指向应用商店中的应用程序。

对于那些在许多年后阅读此内容的人,这可能是相关的:https://web.dev/pwa-url-handler/ -- 你会注意到对此的支持正在逐步淘汰。这可能是更好的选择:https://github.com/WICG/pwa-url-handler/blob/main/handle_links/explainer.md - Swivel

11

这是我完成它的方法。你的应用程序需要在安装时安装几个reg键,然后在任何浏览器中,您只需链接到foo:\anythingHere.txt,它就会打开您的应用程序并将该值传递给它。

这不是我的代码,只是我在搜索相同问题时在网上找到的。只需将下面的所有“foo”更改为您想要的协议名称,并将路径也更改为您的exe。

(将此内容放入文本文件中,另存为foo.reg在桌面上,然后双击它以安装键) -----以下内容放入.reg文件中(不包括此行)------

REGEDIT4

[HKEY_CLASSES_ROOT\foo]
@="URL:foo Protocol"
"URL Protocol"=""

[HKEY_CLASSES_ROOT\foo\shell]

[HKEY_CLASSES_ROOT\foo\shell\open]

[HKEY_CLASSES_ROOT\foo\shell\open\command]
@="\"C:\\Program Files (x86)\\Notepad++\\notepad++.exe\" \"%1\"" 

5
这在 Chrome 中不起作用,这是具体的问题。 - Kjetil Watnedal
1
@KjetilWatnedal:在Chrome中(至少在v40+中)使用此解决方案可以正常工作。与最初的问题相关,OP希望浏览器自动向站点提交某些内容,显然没有本地处理程序可能无法实现。 - Marcel N.
7
我想让大家知道他的解决方案在Chrome浏览器中确实可行(今天在版本49.0.2623.87中进行了测试)。但是,我发现如果您直接在浏览器中输入此协议(foo://C:/test.txt),您可能需要使用ctrl+enter,因为浏览器无法立即识别该协议,搜索协议会在操作系统之前截取该动作。将其放在链接中可以正常工作。 - timmy
@timmy非常感谢,我本来以为我的用户只能使用Internet Explorer。 - Felipe
有人能展示一个reg文件的例子,其中实际的chrome.exe打开特定网站和该网站上的特定页面,以处理打开的协议页面吗? - user280109
显示剩余2条评论

2

我不确定这是否是发布我的答案的正确地方,但由于我找到了很少有用的线索,而这是其中之一,所以我在此处发布我的解决方案。

问题:我希望在Chromium中单击mailto链接时,Linux Mint 19.2 Cinnamon可以打开Evolution。 Gmail被注册为chrome:// settings / handlers中的默认处理程序,我无法选择其他处理程序。

解决方案: 在控制台中使用xdg-settings

xdg-settings set default-url-scheme-handler mailto org.gnome.Evolution.desktop

解决方案在此处找到:https://alt.os.linux.ubuntu.narkive.com/U3Gy7inF/kubuntu-mailto-links-in-chrome-doesn-t-open-evolution,并针对我的情况进行了调整。


1
我发现Jun Hsieh和MuffinMan提供的解决方案通常适用于在Chrome中点击页面链接或粘贴到URL栏中,但在特定情况下(通过命令行传递字符串),它似乎无效。
例如,以下两个命令都会打开一个空白的Chrome窗口,然后什么也不做。
"c:\Program Files (x86)\Google\Chrome\Application\chrome.exe" "foo://C:/test.txt"
"c:\Program Files (x86)\Google\Chrome\Application\chrome.exe" --new-window "foo://C:/test.txt"

为了比较,使用这两个命令之一将http或https URL传递给Chrome会打开网页。
这是因为我们的一个客户报告说,在Adobe Reader中显示的PDF中点击我们产品的链接时,当Chrome是默认浏览器时无法调用我们的产品。(在默认情况下,MSIE和Firefox可以正常工作,但不适用于Chrome或Edge。)
我猜想,Adobe产品找到了默认浏览器(在这种情况下是Chrome),然后通过命令行传递URL,而不是只告诉Windows调用URL并让Windows解决问题。
如果有人知道Chrome安全或其他设置可能与此相关,使Chrome能够完全处理协议处理程序,即使它是通过命令行提供的,我会很感兴趣。我一直在寻找,但目前还没有找到任何东西。
我一直在针对Chrome 88.0.4324.182进行测试。

-1

打开

C:\Users\<Username>\AppData\Local\Google\Chrome\User Data\Default

打开 偏好设置,然后搜索 excluded_schemes,你会在“协议处理程序”中找到它。删除这些被排除的方案,以将 Chrome 重置为使用默认应用程序打开 URL。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接