H5打开app

缘起

运营会给用户发一些营销和通知短信,短信会携带一个网址。领导希望打开对应网页的时候会弹窗询问客户是否使用app打开,能打开就直接在app打开了。

1
2
3
4
5
graph LR
A(点开链接) --> B[打开网页]
B --> C{弹窗提示是否app打开}
C --YES --> 判断
C -- NO --> 正常浏览

scheme

最常用的方式是 scheme

经过测试,我们app的协议是

1
<a href="cn.wangxiao.zhuntiku://zdwx?param=%7B%22Type%22%3A2%2C%22TypeAction%22%3A0%2C%22Data%22%3A%7B%7D%7D">123</a>

代码由三部分组成:

  • cn.wangxiao.zhuntiku:// 。这个类似于 http:// 是一种协议
  • zdwx 。这个类似于 www.baidu.com 是url网址
  • ?param=xxx。 携带的参数

我们可以在页面里创建一个 iframe 或者使用js 跳转页面。

如果有app的话就会提示是否打开

问题

  • 有浏览器会直接报错,错误的页面
  • 不是所有用户都安装了app
  • 手机浏览器 Android Chrome 25+ 不再支持 scheme 只支持 intent://协议,需要用户手动点击才能跳转
  • 微信里不支持,除非是白名单,需要提示在页面里提示浏览器打开
1
2
3
<a href="intent://scan/#Intent;scheme=zxing;package=com.google.zxing.client.android;S.browser_fallback_url=http%3A%2F%2Fzxing.org;end"> Take a QR code </a>
<iframe href="intent://xxx" style="display: none;">></iframe>// 失效
<iframe href="strange://xxx" style="display: none;">></iframe>// 失效

intent 协议

1
2
3
4
5
6
intent://
scan/
#Intent;
scheme=zxing;package=com.google.zxing.client.android;
S.browser_fallback_url=http%3A%2F%2Fzxing.org;
end

这个玩意也有兼容问题:

引用别人的文章 https://www.jianshu.com/p/76eaa1e0c2b2

目前市面上大多第三方浏览器都是基于 Chrome 开发,这就带来了兼容性问题(没有条件覆盖所有的系统浏览器,这里只是有限测试的结果):

1、部分浏览器,只支持 协议手动唤起,如chrome、锤子。

2、部分浏览器只支持 scheme唤起,如 UC 浏览器。

3、大部分浏览器,同时支持 scheme私有协议和intent://协议 自动唤起。但,都没有按标准的 intent://协议来实现(除了 360 浏览器,给 360 点个赞):

  • 有的浏览器在 App 没安装时并没有执行S.browser_fallback_url,而是跳转到应用市场如猎豹浏览器 4.46.3、乐视浏览器 1.2.1.29。
  • 有的浏览器不支持S.browser_fallback_url如搜狗浏览器、欧朋浏览器、猎豹浏览器。
  • 有的浏览器无论应用有无安装S.browser_fallback_url一直都会执行如 QQ 浏览器。

所以对这部分浏览器,不能使用 intent://协议。

4、更奇葩者,二者都不支持,如百度浏览器。

第一种,手动唤起。

第二种,第三种,自定义 scheme

第四种,百度浏览器无解。

解决方式: 判断常用浏览器,如果是锤子和Chrome原生无解,只能避免误伤。

考虑到浏览器判断的难度,结合浏览器市场占有率的情况,我们最终的方案是暂时忽略 锤子系统浏览器、 Chrome 原生浏览器 这部分不支持 自定义 scheme 自动唤起 App 的用户。

链接直接唤起app

如果是短信里直接唤起app,会弹窗提示用app打开还是浏览器打开。要多一次选择,所以在 android6开始支持 deep links 点击链接直达 app

ios得使用 universal links ,要不然还是打开浏览器

结论: 从短信直接唤起app能不能行?

  • 安卓类用户 首选 deep links 安卓6+ 备选 inten-filter
  • iOS 用户首选 universal links ios9+

用户需要区分,不好用,还是得打开网页,再唤起app

iframe

无法明确判断是否安装了app,可以使用 setTimeout 尝试唤起app,如果没有唤起成功会触发下载行为

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
var url = {}
var iframe = document.createElement("iframe")
var body = document.body
iframe.style.cssText='display:none;width:0;height:0'
var timer = null

$('#btn').on("click",function(){
if(/MicroMessenger/gi.test(navigator.userAgent)){
// 引导浏览器打开
}else{
body.appendChild(iframe)
iframe.src = url.url
timer = setTimeout(function(){
window.location.href = url.down
},500)
}
})
1
2
3
4
5
pageshow 事件,页面显示时候触发。在load事件之后触发
pagehide
visibilitychange 页面隐藏,比如切换tab
document.hidden 页面是否隐藏
由于各个浏览器的支持情况不同,我们需要将这些事件都给绑定上,即使这样,也不一定能够保证所有的浏览器都能够解决掉这个小问题,实在没办法的事情就不管了。

参考链接

一切为了营收!如何从推广短信链接唤起 App ?

扫一扫,分享到微信

请我喝杯咖啡吧~