为了降低开发成本,提高开发效率,目前很多app都是在webview中载入h5页面,即hybrid app。在这种开发模式下,web是如何与native交互的呢?以android为例,为大家分享几种web与native的交互方式。




android 与js传参 js与安卓交互_android


这里主要为大家分享js调用native的三种方式,以及在项目中是如何使用的?

1、js调用native的方式

方法1:通过Webview的addJavascriptInterface()实现对象映射

  • 原理:通过WebView的addJavascriptInterface()给浏览器window对象注入一个命名空间,然后web通过命名空间即可调用native方法 。


android 与js传参 js与安卓交互_android 与js传参_02


  • android代码实现


android 与js传参 js与安卓交互_android 与js传参_03


android 与js传参 js与安卓交互_ide_04


  • js代码实现


android 与js传参 js与安卓交互_android_05


  • 总结
  • 虽然使用简单,但android 4.2以下存在严重的。适用于android 4.2以上相对简单的交互场景。
  • 产生的原因:当js拿到android对象后,就可以调用这个android对象中的所用方法,包括系统类(java.lang.Runtime类),从而进行任意代码执行。

方法2:通过WebChromeClient的onJsPrompt()/onJsConfirm()/onJsAlert()拦截JS对话框对应方法

  • 原理:web通过window对话框传递schema,native拦截schema,如果符合约定scheme,然后分发给native对应的方法去处理。


android 与js传参 js与安卓交互_android js交互_06


  • schema格式

约定schema格式:jsbridge://xm?arg1=111&arg2=222&arg3=xx

  • android代码实现:


android 与js传参 js与安卓交互_android 与js传参_07


  • js代码实现


android 与js传参 js与安卓交互_android 与js传参_08


  • 总结
  • 不存在安全问题,能满足大多数的交互场景。

方法3:通过WebViewClient 的shouldOverrideUrlLoading()拦截url

  • 原理:拦截跳转页面的URL,然后对scheme进行解析,如果符合规则就调用native的相应方法进行处理。


android 与js传参 js与安卓交互_android 与js传参_09


  • schema格式:jsbridge://xm?arg1=111&arg2=222&arg3=xx
  • android代码实现


android 与js传参 js与安卓交互_android js交互_10


  • js代码实现


android 与js传参 js与安卓交互_android 与js传参_11


  • 总结
  • 不存在安全问题,适用于不需要返回值情况的互动场景。IOS主要使用该方式。web跳转到native 页面通过url scheme的形式比较方便。

2、项目中如何使用呢?

在js代码中,如果想要这样调用native方法,该如何实现呢?


android 与js传参 js与安卓交互_ide_12


以方法3为例,即通过WebChromeClient的onJsPrompt()拦截JS window.prompt(),实现对native方法的调用。


android 与js传参 js与安卓交互_android js交互_13


  • native逻辑流程图:


android 与js传参 js与安卓交互_ide_14


  • js简化实现代码(jsbridge.js)


android 与js传参 js与安卓交互_ide_15


  • android简化实现代码(jsCallNative类中方法)


android 与js传参 js与安卓交互_js代码_16


android 与js传参 js与安卓交互_ide_17


项目中使用

  • js代码


android 与js传参 js与安卓交互_js代码_18


  • android代码


android 与js传参 js与安卓交互_android 与js传参_19


3、扩展补充:js与android java通信流程


android 与js传参 js与安卓交互_android js交互_20


如需深入研究,可以通过android studio看一下loadUrl和setWebChromeClient两个方法,你会发现其实web view啥都没干,都是直接调用WebViewProvider对应方法处理的,但是aosp(Android Open Source Project)里面并没有WebViewProvider实现类,它的实现类在chromium内核里。可以下载编译一下chromium的源码,追踪一下调用流程,看最终是怎么设置上监听的。