返回

浏览器协议唤起差异: 统一提示及最佳实践

javascript

浏览器默认提示差异:本地应用唤起的行为不一致

在网页中尝试通过自定义协议 (如 myapp://) 打开本地应用程序时,可能会遇到浏览器展示不同提示的情况,一些提示包含“记住我的选择”复选框,而另一些则没有,这种不一致的行为可能会影响用户体验。 本文分析导致差异的原因,并提供解决方案以控制此行为,尽可能统一提示效果。

差异产生的原因分析

根本原因在于浏览器对安全性的考量和用户体验的权衡。为了防止恶意网站随意调用本地程序,浏览器需要通过用户交互确认这一操作。不同提示背后存在如下逻辑:

  • “记住我的选择”复选框的出现 : 通常,如果用户之前从未通过当前网址(协议头+域名/IP)打开过该自定义协议,浏览器会认为是新的,需要用户明确确认是否信任此操作,复选框的存在可以让用户选择是否每次都确认。

  • 不出现复选框的情况 : 如果用户在特定域名/IP上曾经“信任”过此协议,或用户有全局设定规则允许这类请求时,为了便捷操作,浏览器则可能直接执行应用打开,且不会展示 “记住我的选择”。

浏览器维护了一个信任数据库,根据不同来源和用户交互历史动态地判断是否需要用户进行额外确认。 这正是造成提示不一致的原因。

统一行为:移除复选框

若要移除复选框,需要让浏览器“信任”你的应用协议。核心思路就是模拟用户在此网址对协议的信任,或者明确全局设置不提醒,这里有几种途径可以尝试。

1. 使用 <a href="xxx://"> 标签 (建议方式)

这种方法模拟了用户点击链接的行为,更容易被浏览器视为“用户信任”的体现。

操作步骤:

  1. 在 HTML 中创建一个 <a> 标签,href 属性设置为你的应用协议:
  <a id="open-app-link" href="myapp://">打开本地应用</a>
  1. 通过 JavaScript 模拟用户点击行为:
     function openApp() {
        const link = document.getElementById('open-app-link');
       if(link) {
           link.click();
       }
      }

       // 绑定点击事件到指定按钮或其他元素。
      document.getElementById('open-app-button').addEventListener('click', openApp)

原理: 使用<a>标签可以绕过一些直接通过JavaScript设置 location.href 造成的限制。用户手动点击的体验更能体现用户“有意”进行打开应用的行为,因此浏览器更有可能不在初次打开时出现 “记住选择”。使用 JavaScript 模拟点击是为了增强对代码执行时序的掌控,并能处理 a 标签无法直接满足的操作。

2. 通过 chrome 扩展配置自定义处理协议

如果上述方法不符合你的需求,可以考虑安装一个 chrome 扩展,它在浏览器启动时注入 js 并配置自定义处理协议, 这部分操作更加底层,适合处理复杂情况。

  • 操作步骤:
    1. 创建一个新的 Chrome 扩展程序。 需要至少一个 manifest.json 文件 和一个 background.js 文件。

      manifest.json 的内容可以为:

      {
        "manifest_version": 3,
        "name": "Custom Protocol Handler",
        "version": "1.0",
         "description": "Set custom protocol handlers at startup",
           "background": {
           "service_worker": "background.js"
         },
        "permissions": ["scripting", "storage", "declarativeNetRequest"],
        "host_permissions":[
          "<all_urls>"
        ]
       }
      

      background.js 可以为:

      // 创建或更新规则。可以根据需求更改。这里以全部域名处理举例。
          chrome.declarativeNetRequest.updateDynamicRules({
              removeRuleIds: [1],
              addRules: [{
                  'id': 1,
                  'priority': 1,
                  'action': {
                    'type': 'redirect',
                    'redirect': {
                     url: "myapp://"
                  }
                 },
               'condition': {
                  urlFilter: '*://*',
                   'resourceTypes': ['main_frame'],
      
               }
      
              }],
         });
      
    2. 将此文件夹上传到 Chrome 的扩展程序设置 ( chrome://extensions ).
      原理: 此方法利用Chrome扩展能力,每次在访问网页时,会根据设置,进行规则匹配,并完成自动跳转,从而避免了默认提示框的出现。这种方式功能强大,但也相对复杂。适合批量化操作,以及一些系统级配置调整,对于单个页面简单协议唤起来说,操作略重。

安全建议:

  • 尽量使用 <a href> 的方式,它是相对安全的,也符合标准的 Web 开发实践。
  • 在使用自定义协议唤起本地应用程序时,务必清楚你的代码逻辑。防止因设置错误而带来的安全隐患。
  • 对于 chrome 扩展,谨慎安装和使用,确保扩展来源可靠。尽量通过正规的渠道安装,不乱用不明来源的扩展程序。
  • 用户设备和用户浏览器环境复杂,可能存在意料之外的行为,可以做一些额外检测和提示。 例如当点击跳转无效的时候,提供更人性化的交互和解决提示。

结合实际情况选择适合你的方法, 并采取适当的安全措施。