更新记录

1.0.0(2026-04-07) 下载此版本

  • 初始版本
  • 支持安装预加载缓存读取
  • 支持周期性预加载任务注册与结果读取
  • 支持云函数兜底调用
  • 调整为通用预加载桥接插件命名

平台兼容性

uni-app(4.81)

Vue2 Vue3 Chrome Safari app-vue app-nvue Android iOS 鸿蒙
× × × × × × × × API 15
微信小程序 支付宝小程序 抖音小程序 百度小程序 快手小程序 京东小程序 鸿蒙元服务 QQ小程序 飞书小程序 小红书小程序 快应用-华为 快应用-联盟
× × × × × × × × × - × ×

jack-cloud-prefetch

jack-cloud-prefetch 是一个面向 uni-app HarmonyOS 项目的 UTS 插件,用来桥接 Cloud Foundation Kit 的两类能力:

  • cloudResPrefetch
  • cloudFunction.call

它解决的是一类很常见的问题:应用想接入安装预加载和周期性预加载,但业务层又不想直接散落鸿蒙原生 API 调用。插件把预加载读取、周期任务注册、云函数兜底和本地缓存转存统一收口,业务层只需要按需调用即可。

这里有一个边界要先说清楚:

  • 如果 AGC 里的预加载数据来源配置为“开发者服务器”,插件是支持的,因为 cloudResPrefetch 读取到的就是系统从开发者服务器拉取并缓存下来的结果
  • 但当前插件本身不负责主动发起 HTTP 请求去访问你的开发者服务器
  • 如果你希望在“预加载未命中”时继续直连开发者服务器接口,需要像 BabyOne 一样在业务层再包一层普通 API 兜底

适用场景

  • 应用安装后首次打开,希望直接读取安装预加载缓存
  • 应用后续打开,希望通过周期性预加载加速目录页、活动页、专题页等静态数据
  • 预加载未命中时,仍然保留云函数兜底
  • UniApp 项目希望通过 UTS 插件统一桥接 HarmonyOS 预加载能力

平台支持

  • HarmonyOS app-harmony

前提条件

接入前建议先完成下面两件事:

  1. 开通预加载服务并完成 AGC 配置
    官方开发流程:https://developer.huawei.com/consumer/cn/doc/harmonyos-guides/cloudfoundation-prefetch-devprocess

  2. 了解预加载服务能力与限制
    官方文档:https://developer.huawei.com/consumer/cn/doc/harmonyos-guides/cloudfoundation-prefetch-service

如果你的预加载数据来源配置为“开发者服务器”,需要先申请对应权限;如果你走的是云开发,业务层接法类似,只是云侧资源接口换成云函数。

目录结构

uni_modules/jack-cloud-prefetch/
├── package.json
├── readme.md
├── changelog.md
└── utssdk
    ├── interface.uts
    └── app-harmony
        └── index.uts

对外 API

configureJackCloudPrefetch(config)

设置云函数和周期性预加载注册参数。

// #ifdef APP-HARMONY
import { configureJackCloudPrefetch } from '@/uni_modules/jack-cloud-prefetch'

configureJackCloudPrefetch({
  functionName: 'your-prefetch-function',
  functionVersion: '$latest',
  timeout: 10000,
  periodicToken: '',
  periodicParams: '{"scope":"home"}'
})
// #endif

参数:

参数 类型 说明
functionName string 云函数名称,使用云函数兜底时必填
functionVersion string 云函数版本,默认 $latest
timeout number 云函数超时时间,单位毫秒
periodicToken string 注册周期性预加载任务时携带的 token
periodicParams string 注册周期性预加载任务时携带的 params,通常是 JSON 字符串

primeJackCloudPrefetch(options)

应用启动时调用,用来做两件事:

  • 尝试消费一次安装预加载结果,并转存到本地缓存
  • 注册周期性预加载任务
// #ifdef APP-HARMONY
import { primeJackCloudPrefetch } from '@/uni_modules/jack-cloud-prefetch'

await primeJackCloudPrefetch({
  registerPeriodic: true
})
// #endif

返回值:

{
  installCacheReady: true,
  periodicTaskRegistered: true,
  periodicTaskExpireAt: 1760000000000
}

fetchJackCloudPrefetch(options)

按下面顺序读取数据:

  1. 本地转存的安装预加载缓存
  2. 周期性预加载缓存
  3. 云函数兜底
// #ifdef APP-HARMONY
import { fetchJackCloudPrefetch } from '@/uni_modules/jack-cloud-prefetch'

const result = await fetchJackCloudPrefetch({
  preferPeriodicPrefetch: true,
  cloudData: {
    action: 'catalog'
  }
})

console.log(result.source)
console.log(result.data)
// #endif

返回值结构:

{
  source: 'install_prefetch_cache',
  data: {},
  timestamp: 1760000000000,
  token: ''
}

source 可能的取值:

  • install_prefetch_cache
  • periodic_prefetch
  • cloud_function

参数补充:

参数 类型 说明
forceCloud boolean 忽略本地预加载,直接走云函数
preferPeriodicPrefetch boolean 是否优先读取周期性预加载
installOnly boolean 只允许读取安装预加载
skipCloudFunctionFallback boolean 预加载没命中时不走云函数,直接抛错
cloudData object 云函数兜底时传给 cloudFunction.calldata

callJackCloudFunction(options)

直接调用配置好的云函数。

// #ifdef APP-HARMONY
import { callJackCloudFunction } from '@/uni_modules/jack-cloud-prefetch'

const result = await callJackCloudFunction({
  data: {
    action: 'book',
    code: 'cet4'
  }
})
// #endif

getJackCloudPrefetchState()

读取当前预加载状态。

// #ifdef APP-HARMONY
import { getJackCloudPrefetchState } from '@/uni_modules/jack-cloud-prefetch'

const state = getJackCloudPrefetchState()
console.log(state)
// #endif

clearJackCloudPrefetchInstallCache()

清理本地转存的安装预加载缓存。

// #ifdef APP-HARMONY
import { clearJackCloudPrefetchInstallCache } from '@/uni_modules/jack-cloud-prefetch'

clearJackCloudPrefetchInstallCache()
// #endif

推荐接入方式

1. 在业务层包一层服务

不要让页面直接依赖插件。推荐做法是:业务层统一封装,页面只关心 sourcedata

下面是 BabyOne 背单词模块的接法,插件是通用的,但业务包装仍然可以保留自己的领域命名。

import { getWordbookBook as getWordbookBookFromApi, getWordbookCatalog as getWordbookCatalogFromApi } from '@/utils/api.js'

// #ifdef APP-HARMONY
import {
  clearJackCloudPrefetchInstallCache,
  configureJackCloudPrefetch,
  fetchJackCloudPrefetch,
  primeJackCloudPrefetch
} from '@/uni_modules/jack-cloud-prefetch'
// #endif

const ENABLE_WORDBOOK_PREFETCH = true

let wordbookPrefetchPrimePromise = null
let wordbookPrefetchConfigured = false

function ensureWordbookPrefetchConfigured() {
  // #ifdef APP-HARMONY
  if (wordbookPrefetchConfigured) {
    return
  }

  configureJackCloudPrefetch({
    functionName: 'jack-wordbook-cloud',
    functionVersion: '$latest',
    timeout: 10000,
    periodicParams: '{"scope":"catalog"}'
  })
  wordbookPrefetchConfigured = true
  // #endif
}

function unwrapWordbookPayload(payload) {
  if (payload && payload.success === true && payload.data) {
    return payload.data
  }
  return payload || {}
}

function createWordbookResponse(source, payload, timestamp = Date.now(), token = '') {
  return {
    source,
    data: unwrapWordbookPayload(payload),
    timestamp,
    token
  }
}

export async function primeWordbookPrefetch() {
  // #ifdef APP-HARMONY
  if (!ENABLE_WORDBOOK_PREFETCH) {
    return null
  }

  ensureWordbookPrefetchConfigured()

  if (!wordbookPrefetchPrimePromise) {
    wordbookPrefetchPrimePromise = primeJackCloudPrefetch({
      registerPeriodic: true
    }).catch((error) => {
      console.warn('初始化词书预加载失败:', error)
      return null
    })
  }

  return wordbookPrefetchPrimePromise
  // #endif

  return null
}

export async function loadWordbookCatalog(options = {}) {
  const forceRefresh = options === true || options?.forceRefresh === true

  // #ifdef APP-HARMONY
  if (ENABLE_WORDBOOK_PREFETCH) {
    ensureWordbookPrefetchConfigured()

    if (forceRefresh) {
      try {
        clearJackCloudPrefetchInstallCache()
      } catch (error) {
        console.warn('清理词书安装预加载缓存失败:', error)
      }
    } else {
      await primeWordbookPrefetch()
      try {
        const result = await fetchJackCloudPrefetch({
          preferPeriodicPrefetch: true,
          skipCloudFunctionFallback: true,
          cloudData: {
            action: 'catalog'
          }
        })
        return createWordbookResponse(
          result?.source || 'prefetch_cache',
          result?.data,
          result?.timestamp,
          result?.token || ''
        )
      } catch (error) {
        console.warn('读取词书预加载失败,改为请求开发者服务器:', error)
      }
    }
  }
  // #endif

  const res = await getWordbookCatalogFromApi()
  return createWordbookResponse('server_api', res?.data, Date.now())
}

export async function loadWordbookBook(code) {
  const res = await getWordbookBookFromApi(code)
  return createWordbookResponse('server_api', res?.data, Date.now())
}

2. 在 App 启动时先消费安装预加载

// App.vue
// #ifdef APP-HARMONY
import { primeWordbookPrefetch } from '@/utils/wordbook-service.js'
// #endif

export default {
  onLaunch() {
    // #ifdef APP-HARMONY
    primeWordbookPrefetch()
    // #endif
  }
}

注意事项

  1. 安装预加载缓存只能消费一次,所以插件内部会把结果转存到本地缓存
  2. 周期性预加载不是注册后立刻可用,系统会按自己的节奏拉取数据
  3. 周期性任务注册间隔要大于 12 小时,建议按 24 小时或更长的周期处理
  4. 如果你要走云函数兜底,记得先配置 functionName
  5. 预加载更适合目录页、活动页、首屏静态数据,不适合塞入过大的详情数据

官方文档

隐私、权限声明

1. 本插件需要申请的系统权限列表:

需要网络权限以调用云函数与预加载服务

2. 本插件采集的数据、发送的服务器地址、以及数据用途说明:

插件不采集任何数据

3. 本插件是否包含广告,如包含需详细说明广告表达方式、展示频率:

许可协议

MIT协议

暂无用户评论。