【HarmonyOS Next】跨模块交互的事件路由

  • 本文所有代码案例均基于Api12。

如果一个工程中,已经使用分模块开发,多个项目要耦合到一起,难免会遇到跨模块的方法调用。在业务层,仓库A直接调用仓库B,就构成了引用,想避免引用就需要一个中间库帮他们传递消息。

AB双方约定好消息路由,分实现、注册、调用,三步实现通信。

1、创建事件路由名和实现对象: 创建实现对象,在指定方法内实现路由方法

typescript 复制代码
// 路由地址,根据需要命名
let testRouter: CustomURL.Key = new CustomURL.Key("test_path")

// 路由方法实现对象,需要继承自CustomEventRouter.Protocol 
export class TestEventRouter implements CustomEventRouter.Protocol {

  registerRouter(navigator: CustomEventRouter.Navigator): void {

    navigator.handleEvent(testRouter, (params: Record<string, Object>) => {
      // xxxxxxx
      return undefined
    })

  }
}

2、注册: APP启动后将路由对象注册给事件路由

scss 复制代码
  // 不同模块下的实现对象可以分别注入
  CustomEventRouter.registerModule(new TestEventRouter(), new Test1EventRouter())
  CustomEventRouter.registerModule(new Test2EventRouter())

3、调用: 根据路由名调用方法并获取返回参数

javascript 复制代码
  // 根据实际需要接收返回值,如果没有设置返回值,可以不接收
  let result: Object = CustomEventRouter.open(testRouter)

这样一个事件路由就做好了。


事件路由的核心代码:

typescript 复制代码
/**
 * 路由地址的声明。起到代码约束功能
 */
export namespace CustomURL {
  /**
   * 路由地址的数据类型,约束业务模块调用规范
   */
  export class Key {
    // 真实的路由地址
    path: string

    constructor(path: string) {
      this.path = path
    }
  }
}

export namespace CustomEventRouter {

  /**
   * 调用打开路由
   * @param url 路由地址
   * @param paramter 参数
   * @returns 路由实现方法的回调
   */
  export function open(
    url: CustomURL.Key,
    paramter?: Object
  ): ESObject {
    if (baseNavigator.has(url.path)) {
      let objFunc: Function | undefined = baseNavigator.get(url.path)
      if (objFunc) {
        return objFunc(paramter)
      }
    }
  }

  /**
   * 注册路由实现对象的方法,每个模块需自己实现Protocol接口,app启动后在适当的时机调用该方法实现注册,如Index.ets文件
   * @param items 实现路由注册接口的对象
   */
  export function registerModule(...items: Protocol[]) {
    let navigator: Navigator = new Navigator()
    items.forEach((item: Protocol, index: number, array: Protocol[]) => {
      item.registerRouter(navigator)
    })
  }

  /**
   * 移除指定路由
   * @param items 要移除的路由URL
   */
  export function removeURL(...items: CustomURL.Key[]) {
    items.forEach((url: CustomURL.Key, index: number, array: CustomURL.Key[]) => {
      baseNavigator.delete(url.path)
    })
  }

  /**
   * 需要业务组件去实现的路由接口。用协议实现对其他模块方法的调用
   */
  export interface Protocol {
    /**
     * 在这个方法中注册路由
     * @param navigator 注册的规范对象
     */
    registerRouter(navigator: Navigator): void
  }

  /**
   * RouteNavigator是用来注册的model,对代码规范约束的功能。不对外直接暴露baseNavigator,是避免map类型被错误操作
   */
  export class Navigator {
    /**
     * 调用这个方法实现注册单条路由
     * @param key 路由地址
     * @param value 实现方法,Function跟系统用法相同
     */
    handleEvent(key: CustomURL.Key, value: Function) {
      baseNavigator[key.path] = value
    }
  }

  /**
   * 实际存储路由和方法的对象。因为是map,不对外部文件暴露,避免错误操作
   */
  const baseNavigator: Map<string, Function> = new Map()
}
  • 关于本文中使用到【ESObject】的说明: 在鸿蒙当前的版本中,已经不允许直接使用any类型操作对象,检查规则会报错。官方文档给了说明,他们统计过必须使用any的代码不到1%,如果特殊场景下,也给出了替代方案: declare type ESObject = any; 在本文中,因为需要和Function对齐传参,所以使用了替代方案声明参数。
相关推荐
Justin在掘金1 天前
鸿蒙端 SDK 创建、单元测试、发布与依赖完整指南
harmonyos
小雨青年1 天前
鸿蒙 HarmonyOS 6 | 混合开发 (01) Web 组件内核——ArkWeb 加载机制与 Cookie 管理
前端·华为·harmonyos
Swift社区1 天前
ArkUI 的状态管理,其实很多人都用错了
架构·harmonyos
互联网散修1 天前
零基础鸿蒙应用开发第四节:运算符与运算规则
华为·harmonyos
恋猫de小郭1 天前
Flutter 鸿蒙 2026 路线发布,加速同步官方生态,进一步优化体验
前端·flutter·harmonyos
亚历克斯神1 天前
Flutter 三方库 fft 的鸿蒙化适配指南 - 实现端侧高性能快速傅里叶变换、支持音频频谱分析与信号处理域的频域特征提取实战
flutter·harmonyos·鸿蒙·openharmony
爱学习的小齐哥哥1 天前
鸿蒙常见问题分析三:视频关键帧提取与智能体图像分析
人工智能·pytorch·深度学习·harmonyos·harmony pc·harmonyos app
盐焗西兰花1 天前
鸿蒙学习实战之路-Share Kit系列(11/17)-目标应用接收分享(分享详情页)
学习·华为·harmonyos
互联网散修1 天前
零基础鸿蒙应用开发第二节:开发工具的功能介绍
华为·harmonyos
UnicornDev1 天前
【HarmonyOS 6】个人中心数据可视化实战
华为·harmonyos·arkts·鸿蒙·鸿蒙系统