【锁定直播】字节、华为云、阿里云等技术专家讨论如何将大模型接入 AIOps 解决实际问题,戳>>> 了解详情
写点什么

Native 与 Weex 交互通用解决方案

  • 2020-10-26
  • 本文字数:4428 字

    阅读完需:约 15 分钟

Native 与 Weex 交互通用解决方案

背景

从 2018 年开始,有赞移动团队使用 Weex 做为移动端跨平台动态性技术解决方案。自 Weex引入之后需求推进速度得到很大提升,因此被开发同学使用到各个 App和各个模块中,在使用过程中各个 App为了 Weex调用 Native功能,都各自实现了不同功能的 WeexModule,经过 2 年多的发展,发现各个 App中有很多功能差不多的 WeexModule,例如:专用于路由跳转、配置中心、账号信息等类似功能的 WeexModule


我们期望能有一个解决 Native 与 Weex 交互的通用解决方案,简化业务方接入工作,也方便同个 Weex页面可以在不同模块或者不同 App进行正常渲染,因此 ZanWeexModuleSDK就孕育而生。下面将带大家逐步解析 ZanWeexModuleSDK设计方案。

一、现状分析

我们首先分析一个有赞通用的 NativeWeex交互流程图:



从上图我们可以看到,一个完善的基础 WeexAPP它会有有很多个 WeexModule用于 WeexNative组件进行交互,常用的就是路由、网络请求、配置中心、埋点、日志、基础 UI 调用、分享这些重要功能。并且还有很多模块如:IM业务模块、商品业务模块等也有 Weex页面。当我们再去看多个 App 或模块时,就有下图的现状。



上图是不同 App或业务模块都有各自实现的 WeexModule并相互独立,当有业务需求将一个 App或业务模块的 Weex页面迁移到另外 App 或业务模块里,在 WeexModule上的工作量就非常大,既要梳理两个 WeexModule的逻辑差异,又要重新合并逻辑。所以非常需要一套通用 WeexMoudle规则,来做到规范和统一。

二、整体设计

我们通过分析各个 App在使用不同功能的 WeexMoule场景和实现,发现有大部分的功能都是重叠的,只有少部分 App特有逻辑,因此我们进行了这样的改造:



从上图中我们可以看到,通用 WeexModule把各个业务的 WeexModule逻辑全部收拢,简单业务接入通用 WeexModule就只需要关心 Weex代码实现,不用再关心业务使用的 WeexModule实现内容。并且也能做到同个 Weex页面可以在不同模块或者不同 App进行正常渲染。

2.1 筛选通用 WeexModule

有了整体设计方案接下来我们就要分析具体怎么筛选出这些 WeexModule。想要打造一个完善的 Weex通用 MoudleSDK规范不是一口气吃成胖子,设计出来的 SDK差异越大越复杂,接入成本就会越高,推动接入就越不容易,所以需要一步一步来。第一个版本只包含最通用的模块,简化接口设计和集成方式。


所以总结出以下筛选原则:


  • WeexModule复用度高

  • WeexModule的接入、使用方便

  • 新旧接口尽量保持一致


通过以上原则,筛选出第一版的通用 module并简单介绍下:


  • 网络 Module :替换每个 Weex自己实现网络请求封装类, Weex上使用方式保不变

  • 路由 Module :简单路由已实现,独立业务提供自定义实现,接入使用方便

  • 配置 Module :获取移动端动态配置的配置数据, Weex无需重新解析,直接返回的是 Map

  • 日志 Module : Debug本地日志打印, Release日志上传服务器,使用方便

  • 通知 Module :用于跨页面通知状态变化,使用方便

  • 埋点 Module : Weex上使用方式不变,方便 ZWeexManager进行 init 时候不用在实现 IZWeexService

  • 账号 Module :常用来判断登陆状态和获取登陆信息


具体怎么筛选的,举两个选择出的例子:

路由 Module

路由module是非常通用的 WeexModule,它需要处理跳转到各个不同实现的页面,如:NativeWeexFlutterH5,所以 WeexSdk直接提供 navigator的是肯定无法满足各个 App的, 所以各个 App就有了各自不同的路由 module,为了做到后续将各个 AppWeex相关和 Native交互都统一走 ZanWeexModule,所以设计了 ZanNavigatorModule,而 ZanNavigatorModule用法上也和原先一样

网络 Module

卡门网关是有赞移动端依赖的对外网络请求网关,之前各个 AppWeex网络请求依赖的是在 WXStreamModule提供的网络请求能力,让后自己封装一个工具类,用于处理卡门网络请求。而各个 App 的 Native网络请求都已统一使用 ZanRemote二方库提供的卡门网关网络请求能力,卡门网络请求一旦有改动 ZanRemote二方库升级了,而 Weex的封装类没进行修改升级,就会导致 WeexNative不一致,产生请求问题,而这种问题也不容易排查,可能会产生故障。因此我们需要 WeexNative统一使用一套网络请求能力,所以需要提供一个 WeexModule处理网络请求,因此有了 ZanCarmenModule,在用法上还保持了以前封装类的使用方式,方便快速替换


有了这些通用 Module就能很好的支持业务方在实际开发中使用。通用 Module选出来了,那接下来我们就可以对各个 WeexModule去设计了。

3.2 WeexModule设计思路

针对那些可能存在自定义逻辑的 WeexModule,所以在设计的时候需要实现公共部分,并且提供接口给到使用方设置自己的逻辑,例如:路由Module,业务方会存在一些跳转到自己指定的页面场景


/** * 自定义处理Navigator */public interface WXMNavigatorService extends WXMBaseService {    /**     *      * @param context 上下文     * @param uri weex模块标示     * @param url 路径     * @param params 可选参数     * @return     */    boolean navigator(Context context, String uri, String url, JSONObject params);
}
复制代码


  • 怎么使用这 WXMNavigatorService个接口,让相应的 WeexModule找到对应的 WXMNavigatorService接口?为此我们在 WeexModuleManager管理类里提供里一个 serviceMap保存 WXMBaseService实例,让后给到用于查询使用


public class WeexModuleManager {  /**     * 根据默认uri区分weex模块,或者使用自定义字符串     */    private final HashMap<String,HashMap<Class,WXMBaseService>> serviceMap = new HashMap<>(); /**     * 获取sevice     * @param uri 唯一标示     * @param clazz service类型     * @return      */    public WXMBaseService getService(String uri,Class clazz){        ...    }    /**     * 根据uri区分weex模块     * @param uri  唯一标示     * @param clazz service类型     * @param service service实现类     */    public void setService(String uri,Class clazz,WXMBaseService service){     ...    }}
复制代码


通过 WeexModuleManager 提供的 getService 方法我们可以在 WeexMoudle 里找到业务方法实现 WXMBaseService 调用对应的方法,传递参数给到业务方。

3.3 针对 weex回调参数设计规则

各个 module处理完之后,抛给 Weex页面的回调必须要有统一的规则,不然在接入的难度上会有所提高,为了统一规范和降低接入成本,所以我们需要一个通用的回调规范:


 /**     * 带回调的跳转     * @param url  格式 app_name://pageName 和 https://     * @param params  跳转到相应页面需要的数据,相应页面不需要数据可不传 {"key1":"value"}     * @param jsCallback   触发后回调 返回值格式:{"code":200,"data":{},"message":"","success":true}     */    @JSMethod    public void open(String url, JSONObject params, JSCallback jsCallback) {       ...    }
复制代码


其中入参格式的定义,url 是按照已有的标准用于区分 Native跳转、 H5Weex跳转,params 方便使用方不用再做解析操作以及和 iOS 统一返回定义成 JSONObject,其中 jsCallback内部返回值是重点设计,为了保障各个 WeexModule以及以后的 WeexModule统一规范返回格式,模仿采用了后端返回值格式,让 Weex将其当作类似网络异步请求,在使用的时候就可以统一使用回调返回方法处理。


我们通过以上步骤分析把 ZanWeexModuleSdk 设计出来了,接下来我们下在 Weex中具体怎么使用。

三、实践

3.1 业务方接入

Native中初始化

在 native 中需要初始化 WeexModuleManager并且把自定义实现类注册到 WeexModuleManager中。


 //application中初始化   public void initWeex() {       WeexModuleManager.init(app());       //自定义路由跳转       WeexModuleManager.get().setService(AppConfig.WEEX_URI,ZanWXMNavigatorService.class,new ZanWXMNavigatorService());   }
复制代码

Weex中如何使用

我们看下新的 ZanCarmenModule具体使用并且对比下老的方式请求网络, ZanCarmenModuleWeex中对应的唯一标示 zwm-carmen,调用 ZanRemote二方库提供的卡门网络请求能力,方便进行卡门请求。


const carmen = weex.requireModule('zwm-carmen')// post方法carmen.post({    url:"wsc.appconfigs/1.0.2/get",    params:{"key":"value"}}, response =>{    if(response.success) {        let data = response.data    }else {    }})

//对比以前通过工具类请求网络import Network from '@common/tool/Network' //封装方法 request(name,page,success,mError) { this.network.request('XXXX/1.0.0/list','POST',{body:{page:page,size:20}},success,mError) } //具体请求 this.request(page, response => { let data = response.data }, error => { } );
复制代码


可以看到新的 ZanCarmenModule相对老的方式写法上更简单,而且调用返回处理也是保持一样。

3.2 问题反馈

随着 ZanWeexModuleSDK完成,陆续在有赞各个 App 进行的 Weex项目中接入使用,如:微商城、零售、美业、精选、有赞客等 App 中,也有如:IM 模块、商品模块、营销模块等模块中,在实际开发使用中小伙伴也给到我们很多意见和吐槽。


  • 小 A:"网络 Module 很方便的,在新的业务模块中网络的直接用就可以了”

  • 小 B:"路由 Module 那个可以再扩展下,现在业务方需要手动处理 NativeWeexH5的路由,可以增加多一点通用实现”

  • 小 C:“日志 Module 要是提供一些高级点的特性就好了,比如识别出对象,就用 json 字符串打印”


大家遇到最多的问题是:虽然提供了 ZanNavigatorModule,但并没有实现很多通用的路由跳转,还是要重新实现 WXMNavigatorService,将原有的逻辑复制到 navigator()方法中。

3.3 后续规划

上述这些问题也有后续的规划:


  • 针对类似路由 Module 这种各个端差异大且常用的 WeexModule,是不可能做到一步完成所有替换,因为这种替换会伴随着风险、时间不够、考虑不全等问题。我们先逐步将公共功能剔除出来,放在 ZanWeexModuleSDK中实现,例如:跳转 Weex页面、跳转 H5页面。最后只留下各个 App的差异部分。

  • 针对类似日志 Moudle 这种 Module 会逐步完善使用体验,提供更多更好用的方法。


最后将其做成一个 WeexNative交互的通用解决方案,简化业务方接入工作,只需要关心业务代码。

四、总结

本文主要介绍了 ZanWeexModuleSDK的设计方案。ZanWeexModuleSDK的实现是结合有赞移动团队使用 Weex过程中,各个 AppWeex交互功能重复和代码冗余中产生的,读者在规划使用 Weex开发时就可以考虑这些问题,当然这也不仅仅可以应用在 WeexNative交互,也可以应用在 FlutterNative交互以及 JSNative交互方案上。希望 ZanWeexModuleSDK的设计方案能对你有所帮助。


如果你有比较好的建议,可以评论回复,如有任何问题,欢迎指正。


本文转载自公众号有赞 coder(ID:youzan_coder)。


原文链接


Native 与 Weex 交互通用解决方案


2020-10-26 14:073478

评论

发布
暂无评论
发现更多内容

开心档之boostrap按钮组

雪奈椰子

bootstrap 开心档

天翼云第八代云主机助力企业攻克上云“大象流”加密处理业务难题

天翼云开发者社区

《解构领域驱动设计》-领域驱动设计统一过程

珑彧

Java 读书笔记 架构 方法论 领域驱动设计

JVM说--直接内存的使用

京东科技开发者

JVM io nio 虚拟机 企业号 2 月 PK 榜

开心档之boostrap轮播

雪奈椰子

bootstrap 开心档

领导者!天翼云蝉联政务公有云基础设施市场第一

天翼云开发者社区

舞台LED显示屏对灯光设计产生了哪些影响

Dylan

LED显示屏 全彩LED显示屏 led显示屏厂家

Fastjson踩“坑”记录和“深度”学习

阿里技术

Fastjson

Knative Autoscaler 自定义弹性伸缩

天翼云开发者社区

共铸国云智领未来| 数据进超市,海岛更善治

天翼云开发者社区

3Dmax和C4d有什么区别?

Finovy Cloud

3DMAX

快速入门API Explorer

华为云开发者联盟

云计算 华为云 API Explorer平台 企业号 2 月 PK 榜 华为云开发者联盟

一步一腳印的 iOS App 上架和更新流程

雪奈椰子

ios apple 上架 apps

一文详解数GaussDB(DWS)函数出参带出方式

华为云开发者联盟

数据库 后端 华为云 企业号 2 月 PK 榜 华为云开发者联盟

DAAM:首次利用视觉语言学解释大型扩散模型

Zilliz

开心档之boostrap按钮2

雪奈椰子

bootstrap 开心档

开心档之bootstrap卡片

雪奈椰子

bootstrap 开心档

3D可视化:18个WebGL框架和Web3D图形库

2D3D前端可视化开发

WebGL 三维可视化 web3d 3d绘图引擎

职场IT老手教你3步教你玩转可视化大屏设计,让领导眼前一亮!

葡萄城技术团队

Java程序员:为了跳槽刷完1000道真题,想不到老板直接给我升职了

程序知音

Java java面试 Java面试题 Java面试八股文 后端面试

2023年互联网大厂泄露的这1300多道JAVA面试题,包含了程序员的所有技术点

架构师之道

Java 程序员 java面试

如何将物理机Windows系统迁移到VMware虚拟机?

天翼云开发者社区

带你动手做AI版的垃圾分类

华为云开发者联盟

人工智能 华为云 企业号 2 月 PK 榜 华为云开发者联盟 垃圾分类

如何在 Web 端实现一个多人数独游戏

声网

Vue 互动白板 RTE

开心档之bootstrap折叠

雪奈椰子

bootstrap

“云”上书店,氛围感拉满!

天翼云开发者社区

模块1作业

抹茶柠檬

架构实战营

产研指南针的量化指标实践笔记

车江毅

项目管理 研发管理 降本增效 北极星指标 效能度量

iOS AppStore上架流程图文详解2021版 (上)

雪奈椰子

ios apple 上架 apps

找 ChatGPT 写 SQL? 不如试试 PromQL,三行解决复杂时序场景查询

Greptime 格睿科技

sql 云原生 时序数据库 PromQL 可观测

《福布斯》评英特尔最新财报:业绩之外,制程路线图的稳步推进是真正的好消息

科技之家

Native 与 Weex 交互通用解决方案_移动_黑羽_InfoQ精选文章