预加载和缓存

1. 预加载和缓存概念

预加载和缓存都是为了节省 JSBundle 下载的时间,加快 UI 的渲染。

1.1 预加载

预加载是将下载 JSBundle 的动作提前完成,在需要用到的时候直接从本地读取并渲染。实际项目使用中,可以将需要预加载的 url 地址列表在app启动时提前从服务端获取,通过 Chameleon SDK 提供的预加载能力提前下载下来。

1.2 缓存

对于没有预加载的 JSBundle 在渲染前需要先下载,下载完成后 Chameleon SDK 会缓存此 JSBundle,下次渲染同一个 JSBundle时,如果此 JSBundle 没有更新则不会下载新的,达到节省时间和流量提升渲染速度的目的。

2. JsBundleMgr

JsBundleMgr是一个对js进行下载、缓存的一个模块,根据协议来实现js增量更新功能。主要有以下内容

  1. |
  2. |——cache 基于DiskLrucache来实现缓存功能
  3. |——code js代码的获取及管理
  4. |——net 采用httpUrlConnect实现下载功能
  5. |——utils 工具包
  6. |——CmlJsBundleConstant 常量的管理
  7. |——CmlJsBundleEngine 实现了CmlJsBundleManager接口,入口类
  8. |——CmlJsBundleEnvironment 当前环境的设置,如debug环境等
  9. |——CmlJsBundleManager 实现此接口可自己定义JsBundle的管理
  10. |——CmlJsBundleMgrConfig 配置类,设置预加载js路径、缓存大小等,默认预加载及运行时缓存大小是4M,可自行设置

2.1 code

对js代码进行预加载、获取、缓存的管理。在该包里,我们将拿到的url根据协议来拆分成多个url1、url2等,然后在根据url1、url2等来获取对应的js代码,首先从本地缓存里获取去寻找对应的js代码,如果不存在则从网络去下载并保存在本地

utils

一些文件管理、拆分url、网络判断的工具类

  • CmlCodeUtils:获取到的url、code的拆解及合并
  • CmlFileUtils:sd卡及缓存目录的判断
  • CmlLogUtils:Log的实现
  • CmlNetworkUtils:当前网络状态的判断,如Wi-Fi、4g等
  • CmlUtils:Md5的生成、主线程判断等等

2.2 CmlJsBundleConstant

缓存文件名、预加载优先级的管理,预加载优先级有以下三种类型

  • 普通(PRIORITY_COMMON):非Wi-Fi情况不预加载
  • 强预加载(PRIORITY_FORCE):无论什么网络情况都预加载
  • 强预加载+预解析(PRIORITY_FORCE_MAX):目前未用到

2.3 CmlJsBundleEngine

实现了CmlJsBundleManager接口,主要有以下三个方法

  • initConfig(Context,CmlJsBundleMgrConfig):初始化config,主要是设置预加载url、预加载缓存、运行时缓存的设置,预加载及运行时缓存默认为4M
  • startPreload():开始预加载,目前预加载成功或者失败并没有任何信息返回,只能查看log进行分析
  • getWXTemplate(String,CmlGetCodeStringCallback):获取js代码

2.4 CmlJsBundleManager

实现此接口可以自己定义JsBundleMgr的实现

2.5 使用

添加依赖

  1. compile 'com.didiglobal.chameleon:js-bundle-mgr:latest.version'

预加载

  1. CmlJsBundleEnvironment.DEBUG = true;
  2. List<CmlModel> cmlModels = new ArrayList<>();
  3. CmlModel model = new CmlModel();
  4. model.bundle = CmlUtils.parseWeexUrl(url1);
  5. model.priority = 2;
  6. cmlModels.add(model);
  7. model = new CmlModel();
  8. model.priority = 2;
  9. model.bundle = CmlUtils.parseWeexUrl(url2);
  10. cmlModels.add(model);
  11. CmlJsBundleMgrConfig config = new CmlJsBundleMgrConfig.Builder().setPreloadList(cmlModels).build();
  12. CmlJsBundleEngine.getInstance().initConfig(this, config);
  13. CmlJsBundleEngine.getInstance().startPreload();

获取Js代码

  1. CmlJsBundleEngine.getInstance().initConfig(this, new CmlJsBundleMgrConfig.Builder().build());
  2. String url = CmlUtils.parseWeexUrl(url);
  3. CmlJsBundleEngine.getInstance().getWXTemplate(url, new CmlGetCodeStringCallback() {
  4. @Override
  5. public void onSuccess(String codes) {
  6. Log.i(TAG, "onSuccess: " + codes);
  7. }
  8. @Override
  9. public void onFailed(String errMsg) {
  10. Log.i(TAG, "onFailed: " + errMsg);
  11. }
  12. });