image.png

进程间通信可以使用很多方式来进行消息的传递,比如大家熟悉的管道(pipe)。然而,Eletron 使用了 web worker API postMessage 相同的 structured clone algorithm 来做 IPC 数据的序列化和反序列化。这个方法效率和 JSON 差不太多,在传输大量数据时同样会有性能问题,所以 Electron 推荐使用 CSS animation,而非常不建议做 JS anination。

3. 基于 Canvas 绘制

Canvas绘制是实现UI跨平台的主流思路:

  • 平台渲染: 用 JS 来调用原生 UI, 这是 React Native 采用的方式。优点是大部分时候性能足够好;缺点是 JS bridge 需要适配所有支持的平台,当平台侧UI控件想要在RN中使用,需要开发者花费额外精力去适配。
  • 统一渲染: 用其他技术来模拟原生 UI。这是 Cordova / Electron 采用的方式。优点是代码简单,UI 直接在第三方渲染器(webview)中渲染出来;缺点是 UI 性能受 JS 单线程及 webview 本身渲染性能的影响,在复杂交互时往往表现不佳。

当大多数选择统一渲染方案的技术栈只是把目光停留在了webview ,人们忽略了其实所有的 UI 渲染,最终都是在 canvas 上一个像素一个像素填充出来的。如果做一套系统,略过 dom/css/js 复杂的渲染逻辑,直接定制好各种各样的控件,将其绘制到 canvas 上,是不是可以鱼与熊掌兼得?

做到这点的要数 flutter 了。它使用 chrome 底层的图形渲染引擎 skia,从底向上设计出来一套可以高效工作的控件库,比 webview 性能高的同时,又不依赖平台侧的控件。

image.png

现有跨平台方案中的问题

目前所有这些方案的着眼点还是局限在UI层的跨平台,那么业务逻辑代码怎么办?用JS这样的 UI 层的语言撰写难以保证运行时效率,最终还是要诉诸于 native 语言实现,原本一种语言统一天下的初衷,最终发现要学习三种语言,iOS、android、JS/dart 各来一套(flutter可能做得稍微强一点儿,但是依然需要借助 channel 调用平台侧的服务)。

“相比UI跨平台,如何在业务逻辑层跨平台是一个容易被忽略但更值得被关注的问题。”

那么为什么逻辑层跨平台技术进展如此缓慢呢?一个主要原因是没有一个合适的语言工具,很难找到一门语言能够同时覆盖这么多平台的原生语言的优势。

在 Rust 成熟以前,C/C++ 几乎是跨端做业务逻辑的唯一的选择。用 C/C++ 实现一次,然后在各个端上用静态链接的方式编译到 app 中。当然这免不了要做很薄的一层接口:每个平台原生语言到 C/C++ 的桥接。

但是 C/C++ 的代码(相对于 java/kotlin/swift来说)的撰写难度较高,跨平台编译链接有很多坑要踩,最终会遮掩所谓「一次撰写,到处链接」的好处。

如今有了Rust, Rust 有不输于任何一门现代语言的依赖管理和生态,有非常完备的跨平台编译系统和跨语言FFI支持,而 Rust 本身的不依赖运行时的内存安全和并发安全性,还有几乎最高质量的 webassembly 支持,使其成为 C/C++ 跨平台的完美替代品。除了 rust 本身的跨平台工具链之外,Rust 生态里还有专门为简化与 iOS 原生语言互操作的工具 cargo lipo(封装 C FFI),以及为与 java 互操作的 jni,甚至还有专门针对 Android 的 android-ndk-rs。

接下来,我们需要的就是一套组织各个平台原生语言和 Rust 互操作的思路,来解决通用性的问题。

前端中的后端

所谓前端中的后端,就是在前后端分离的基础上,进一步把前端中偏 UI 的业务逻辑和偏数据处理的业务逻辑分开。而掌管数据处理的这部分功能,我们管它叫前端中的后端。

基本架构

无论是前端架构中被广泛使用的 MVC 还是 MVVC 模式,其第一个 M,Model(包含数据,状态,以及业务逻辑),就是我们要分离出来统一处理的「后端」。借鉴之前提到的 bridge 模式,可以构想出来这么一套前端代码的前后端分离的模型:

image.png

这个模型相对于传统的 UI 跨平台方案,其最大不同是:让所有的相关方处理自己最擅长的事情,而不要强行适配。和平台相关的代码,比如 UI,平台设备的访问等,用更擅长做这件事情的平台原生语言实现(或者 flutter),而平台无关的业务逻辑代码,算法,网络层代码,使用 Rust 来实现。这样,Rust backend 不用去花大量的精力去包裹平台的东西,而只需干好一个 backend 需要干好的事情。

通信方式

之前的 UI 方案,采用的都是 JSON 或者类 JSON 的序列化方案,JSON 是效率非常低下,且类型安全度比较低的一种序列化方案,在这样的场景下,我们还有更多更好效率更高类型更安全的方案,比如 protobuf,flatbuffers 等。

反序列化序列化
image.pngimage.png

以 Rust 和 Kotlin 之间做通信为例,使用 JSON 以及 Protobuf 的通信流程分别如下:

JSONProtobuf
image.pngimage.png

Rust 和 Kotlin 分别将定义好的 protos 编译成平台代码,然后可以在两端自由地传递 protobuf 的数据。

示例

比如要展示电影网站 Tubi 的首页,假设我们基于 clean architecture 的 MVP 结构实现此逻辑

  • 后端提供 API 获取电影列表 GET /api/v1/get_movies
  • 建立一个 TubiRepository 处理网络层的请求
  • 请求的响应被反序列化成 Category / Movie models,然后以 Entity 的形式交给 Use cases
  • 最后presentation layer 将结果被渲染到屏幕

image.png

这里,尝试对 Model层 用Rust实现,如下:

  1. 暴露给 native 层的方法是:getMovies()
  2. getMovies() 内部将参数序列化成 protobuf 传递给一个 Rust 函数 dispatcher
  3. dispatcher 反序列化请求后得知是一个 RequestGetMovies,随后被 dispatch 给 get_movies()
  4. get_movies()从本地 cache 里读取数据,读不到的话通过 reqwest 从远程 API 获取数据并缓存

image.png

从 native 开发者的角度,她就调用了一个 getMovies() 后返回了序列化好的 Movie,Category等数据结构,其它的细节不需要理会。

再举个例子,用户在观看视频的时候,客户端会定期向服务器汇报当前观看的位置

自我介绍一下,小编13年上海交大毕业,曾经在小公司待过,也去过华为、OPPO等大厂,18年进入阿里一直到现在。

深知大多数前端工程师,想要提升技能,往往是自己摸索成长或者是报班学习,但对于培训机构动则几千的学费,着实压力不小。自己不成体系的自学效果低效又漫长,而且极易碰到天花板技术停滞不前!

因此收集整理了一份《2024年Web前端开发全套学习资料》,初衷也很简单,就是希望能够帮助到想自学提升又不知道该从何学起的朋友,同时减轻大家的负担。
img
img
img
img
img

既有适合小白学习的零基础资料,也有适合3年以上经验的小伙伴深入学习提升的进阶课程,基本涵盖了95%以上前端开发知识点,真正体系化!

img
img

由于文件比较大,这里只是将部分目录大纲截图出来,每个节点里面都包含大厂面经、学习笔记、源码讲义、实战项目、讲解视频,并且后续会持续更新
如果你觉得这些内容对你有帮助,可以添加V:vip1024c 备注前端获取(资料价值较高,非无偿)
img

最后

整理面试题,不是让大家去只刷面试题,而是熟悉目前实际面试中常见的考察方式和知识点,做到心中有数,也可以用来自查及完善知识体系。

开源分享:【大厂前端面试题解析+核心总结学习笔记+真实项目实战+最新讲解视频】

《前端基础面试题》,《前端校招面试题精编解析大全》,《前端面试题宝典》,《前端面试题:常用算法》

前端面试题宝典

前端校招面试题详解

片转存中…(img-lcNmcr50-1711577770203)]

[外链图片转存中…(img-DXEcNKx9-1711577770203)]

[外链图片转存中…(img-ykX4PqiI-1711577770203)]

Logo

瓜分20万奖金 获得内推名额 丰厚实物奖励 易参与易上手

更多推荐