杰理 SDK 文档中心
首页
首页
  • 项目概览

    • 项目概述与功能特性
    • 工程结构与运行环境
  • 快速开始

    • SDK 集成步骤
    • 连接方式选择指南
  • 核心 SDK 架构

    • SDK 框架组成
    • JL_OTAManager 升级管理 API
    • 设备认证与广播解析
  • 蓝牙连接与设备发现

    • 设备扫描与广播发现
    • 原生 CoreBluetooth 连接
    • JL_BLEKit SDK 连接
    • JL_Assist 自定义连接
    • GATT Over BR/EDR 经典蓝牙升级
  • OTA 升级工作流

    • 标准升级流程
    • 自动化测试与批量升级
    • 广播音箱升级
    • 升级文件管理
  • 示例工程

    • 完整示例应用
    • 迷你示例工程
    • 第三方依赖与工具
  • 开发支持与版本发布

    • 文档中心与 API 说明
    • SDK 版本与构建产物
    • 调试技巧与日志辅助

标准升级流程

标准升级流程(Normal/Standard OTA Upgrade)是 JL_OTALib 中基于 JL_OTAManager 的常规固件升级链路:设备在正常模式下通过 BLE 连接,完成特性查询、固件分包下发、进度上报、单备份回连与重启收尾,是整个 OTA SDK 最基础、使用最广泛的升级方式。

目的与范围

本文档详细说明「标准升级流程」这一目录项所对应的完整能力:JL_OTAManager 及其代理协议 JL_OTAManagerDelegate、全部状态/结果枚举、标准升级的分步控制流、数据收发机制、配置属性、API 参考以及失败处理。

本文档不涉及以下属于兄弟页面的能力:

  • 4G 升级流程:由 JL4GUpgradeManager(cmdStartUpgrade4G:Data:)实现的蜂窝网络升级,见 JL4GUpgradeManager.h。
  • 强制升级:本文只覆盖 JL_OtaStatusNormal 的正常升级;JL_OtaStatusForce、耳机单备份强制升级(JL_OtaHeadsetYES)、手表资源强制升级(JL_OtaWatchYES)涉及额外的前置条件与回连逻辑,仅在相关枚举处提及。
  • BLE 连接管理:JLBleManager 负责扫描/连接/认证,本文只将其作为升级流程的底层通道引用。
  • 文件系统与 Flash 操作:JL_FileManager、JL_FlashOperateManager 属于独立能力。

概述

OTA(Over-The-Air)升级是蓝牙设备(耳机、音箱、手表等)固件更新的核心能力。JL_OTAManager 是 SDK 提供给上层应用的升级编排器(Orchestrator):它本身不直接持有 BLE 连接,而是通过两个方向与业务层协作:

  1. 上行:业务层把设备回传的数据通过 cmdOtaDataReceive: 喂给管理器;
  2. 下行:管理器通过必选代理方法 otaDataSend: 把待发送指令/固件分包交给业务层,由业务层经 BLE 发出。

这种「管理器-代理」的解耦设计,使得 SDK 不依赖具体蓝牙框架(CoreBluetooth 或厂商私有封装),业务层可以自由控制连接生命周期,同时 SDK 内部专注于升级协议状态机:查询特性 → 判定升级类型 → 分包下发 → 校验 → 单备份回连 → 重启。

标准升级流程的典型触发场景:

  • App 检测到设备固件版本(versionFirmware)低于服务器下发版本;
  • 用户在设备详情页点击「立即升级」;
  • 设备从普通工作模式进入升级流程(区别于强制升级/4G 升级)。

架构

flowchart TD
    subgraph sg_App["App 应用层"]
        Demo["业务层 / Demo"]
        BleMgr["JLBleManager(BLE 连接与收发)"]
    end

    subgraph sg_OTASDK["JL_OTALib SDK 层"]
        OtaMgr["JL_OTAManager(单例)"]
        Delegate["JL_OTAManagerDelegate 回调"]
    end

    subgraph sg_Device["设备端"]
        Device["蓝牙设备(耳机 / 音箱 / 手表)"]
    end

    Demo -->|"配置 UUID/名称/delegate"| OtaMgr
    Demo --> BleMgr
    BleMgr -->|"noteEntityConnected / cmdOtaDataReceive"| OtaMgr
    OtaMgr -->|"otaDataSend 待发送数据"| BleMgr
    OtaMgr --> Delegate
    BleMgr -->|"BLE 读写通道"| Device
    Device -->|"ACK / 状态 / 回连"| BleMgr

架构说明:

  • 业务层负责 BLE 连接管理(JLBleManager)与升级 UI/业务编排,它既是 JL_OTAManager 的配置方,也是其代理回调的接收方。
  • JL_OTAManager 是单例(getOTAManager),内部维护升级状态机、分包序号(mCmdSN)、已传字节数(otaSent)与总长度(otaLength)。
  • 代理回调中 otaDataSend: 为必选方法,是 SDK 输出数据的唯一出口;otaUpgradeResult:Progress:、otaFeatureResult:、otaCancel 为可选方法,用于向 UI 层汇报进度与结果。
  • 设备端与 App 之间始终是 BLE 链路;标准升级中可能发生「断开 → 按 UUID/MAC 回连」以切换至升级模式。

核心组件与关键枚举

JL_OTAManager(升级管理对象)

JL_OTAManager 对外暴露的属性可分为三类:

类别属性说明
设备标识mBLE_UUID / mBLE_NAME需要开发者填入的设备 UUID 与名称
设备能力bleOnly / bleAddr是否仅支持 BLE、蓝牙地址
升级参数otaStatus / otaHeadset / otaWatch / otaPartition / bootloaderType升级类型、耳机单备份、手表资源、单/双备份、是否需要 BootLoader
回连配置otaReconnectTypeUUID 回连或 MAC 地址回连
传输统计otaLength(只读)/ otaSent(只读)设备通知的升级内容总大小 / 已传输大小
协议状态mCmdSN / version / versionFirmware指令序号、设备版本号、设备版本信息

设计意图:设备能力属性(otaPartition、otaStatus 等)不是开发者凭空填写的,而是由 cmdTargetFeature 查询后 SDK 自动填充——这是「先查询、后升级」安全模型的基础,避免对设备实际能力做任何假设。

JL_OTAManagerDelegate(升级回调代理)

/// OTA 升级管理对象回调
@protocol JL_OTAManagerDelegate <NSObject>

/// 即将被发送的数据
/// @param data 数据内容
- (void)otaDataSend:(NSData *_Nonnull)data;

@optional
/// 回调设备状态信息
/// @param manager 对象状态
- (void)otaFeatureResult:(JL_OTAManager *_Nonnull)manager;

/// 回调升级状态以及进度等
/// @param result 状态以及进度信息
/// @param progress 进度信息
- (void)otaUpgradeResult:(JL_OTAResult)result Progress:(float)progress;

/// 取消OTA升级
- (void)otaCancel;

@end

Source: JL_OTAManager.h

设计意图:otaDataSend: 被声明为 @required,因为 SDK 的所有下行数据(特性查询指令、固件分包、重启指令)都必须经由业务层转发到 BLE 通道;缺少该实现,升级链路将完全无法工作。其余三个方法均为可选,业务层按需实现即可。

标准升级核心流程

标准升级在 SDK 视角是一条明确的协议状态机。以下时序图展示了从连接、查询到完成重启的完整链路(以单备份升级为例,双备份设备会跳过回连阶段):

sequenceDiagram
    participant App as App 业务层
    participant Mgr as JL_OTAManager
    participant BLE as BLE 通道
    participant Dev as 设备

    App->>Mgr: getOTAManager 获取单例
    App->>Mgr: 配置 mBLE_UUID / mBLE_NAME / delegate
    BLE-->>Mgr: 连接成功(认证完成)
    App->>Mgr: noteEntityConnected
    App->>Mgr: cmdTargetFeature(连上后第一步)
    Mgr->>BLE: 下发特性查询指令
    BLE-->>Mgr: 设备特性数据(cmdOtaDataReceive)
    Mgr-->>App: otaFeatureResult(填充 otaStatus/otaPartition 等)
    App->>Mgr: cmdOTAData:Result:(标准升级数据)
    loop 分包传输
        Mgr->>App: otaDataSend(业务层经 BLE 发出)
        BLE-->>Mgr: 设备 ACK / 数据(cmdOtaDataReceive)
        Mgr-->>App: otaUpgradeResult:Progress:(进度上报)
    end
    alt 单备份(JL_PartitionSingle)
        Mgr-->>App: JL_OTAResultReconnect / ReconnectWithMacAddr
        App->>Mgr: cmdOtaDataIIResult(回连成功后再次发起)
    end
    Mgr-->>App: otaUpgradeResult JL_OTAResultSuccess
    App->>Mgr: cmdRebootDevice

阶段一:初始化与连接

  1. 通过 [JL_OTAManager getOTAManager] 获取单例(头文件明确标注 init 已废弃,见 JL_OTAManager.h);
  2. 填入 mBLE_UUID、mBLE_NAME,设置 delegate,并按需调用 maxLostCount:(默认丢包上限为 2 次);
  3. 设备完成 BLE 认证后,调用 noteEntityConnected 告知 SDK 连接就绪。

阶段二:特性查询(强制前置步骤)

头文件注释明确规定:cmdTargetFeature 所有情况下都需要执行,而且是在连上后(认证完成)第一步执行(JL_OTAManager.h)。

该查询决定后续升级路径:

  • otaStatus → 正常升级(JL_OtaStatusNormal)还是强制升级(JL_OtaStatusForce);
  • otaPartition → 单备份(JL_PartitionSingle,需回连)还是双备份(JL_PartitionDouble);
  • otaHeadset / otaWatch → 耳机、手表资源是否强制升级;
  • bootloaderType → 是否需要先下载 BootLoader;
  • otaReconnectType → 回连方式按 UUID 还是 MAC 地址。

查询结果通过可选代理 otaFeatureResult: 回调,业务层在该回调中决定是否具备升级条件(例如电量、版本比较)。

阶段三:发起升级与分包传输

调用 cmdOTAData:Result: 传入升级数据(固件文件内容),SDK 内部:

  1. 解析固件信息,校验与设备版本/SN 的匹配性;
  2. 若校验失败,通过 JL_OTA_RT 回调返回 JL_OTAResultFailVerification、JL_OTAResultFailSameSN 或 JL_OTAResultFailKey 等错误;
  3. 校验通过后进入分包下发循环:每一包数据经必选代理 otaDataSend: 交给业务层发送,业务层收到设备回包后调用 cmdOtaDataReceive: 喂回 SDK;
  4. 进度通过 otaUpgradeResult:Progress: 持续上报(progress 为 0.0 ~ 1.0 的浮点值)。

传输过程中 otaSent(已传输字节)与 otaLength(总大小)属性可随时读取,用于 UI 展示。

阶段四:单备份回连(可选分支)

  • 双备份设备:直接进入完成阶段;
  • 单备份设备:SDK 会先通知 JL_OTAResultReconnect(UUID 回连)或 JL_OTAResultReconnectWithMacAddr(MAC 回连),设备断开并重启进入升级模式;业务层完成重连后,调用 cmdOtaDataIIResult:(头文件注明「单备份升级特有!!!」)再次发起升级,该接口可在回连成功后复用已缓存的升级数据(JL_OTAManager.h)。可用 cmdOtaIsRelinking 查询是否正在回连。

阶段五:完成与重启

收到 JL_OTAResultSuccess 后,调用 cmdRebootDevice 让设备重启到新固件;若设备卡死可调用 cmdRebootForceDevice 强制重启。一次完整的升级会话结束后,调用 resetOTAManager 清理内部状态,为下一次升级做准备。

状态机总览

stateDiagram-v2
    [*] --> Idle: 初始化 getOTAManager
    Idle --> Connected: noteEntityConnected
    Connected --> FeatureQuery: cmdTargetFeature
    FeatureQuery --> Ready: otaFeatureResult
    Ready --> Upgrading: cmdOTAData
    Upgrading --> Relinking: 单备份 需回连
    Relinking --> Upgrading: cmdOtaDataIIResult
    Upgrading --> Success: JL_OTAResultSuccess
    Success --> Reboot: cmdRebootDevice
    Upgrading --> Failed: JL_OTAResult 失败码
    Failed --> Idle: resetOTAManager
    Reboot --> Idle

数据收发机制

SDK 与 BLE 通道之间的数据交换是理解整个升级流程的关键:

  • 下行(SDK → 设备):JL_OTAManagerDelegate.otaDataSend:(必选)。业务层在实现中应调用蓝牙写入接口(如 JLBleManager 的写特征方法)将 data 发出。
  • 上行(设备 → SDK):cmdOtaDataReceive:。业务层在蓝牙特征回调中收到数据后,原样传给管理器;管理器内部按协议解析 ACK、状态与升级模式切换通知。
  • 日志开关:logSendData: 可打印 SDK 发送的数据内容,便于联调;logSDKVersion(类方法)返回 SDK 版本号,排查问题时用于对齐版本。

使用示例

以下示例均取自 JL_OTAManager.h 的真实接口声明,并按其文档语义组织为标准升级的典型调用序列。

初始化与配置

/// 获取 OTA 升级对象
+ (JL_OTAManager *)getOTAManager;

/// 设备UUID(需要开发者填入)
@property(strong, nonatomic) NSString *mBLE_UUID;

/// 设备名称(需要开发者填入)
@property(strong, nonatomic) NSString *mBLE_NAME;

/// 设备交互回调代理
@property(weak, nonatomic) id<JL_OTAManagerDelegate> delegate;

/// 当BLE连接上时告知SDK
- (void)noteEntityConnected;

Source: JL_OTAManager.h

特性查询 → 发起标准升级

/// 查询设备OTA信息
/// 所有情况下都需要执行,而且是在连上后(认证完成)第一步执行
- (void)cmdTargetFeature;

/// 开始OTA升级
/// @param data 升级数据
/// @param result 升级结果
- (void)cmdOTAData:(NSData *)data
            Result:(JL_OTA_RT __nullable)result;

/// OTA升级II
/// 单备份升级特有!!!!
/// 此接口可用于 OTA 回连成功后,再次发起升级使用
/// @param result 升级结果回调
- (void)cmdOtaDataIIResult:(JL_OTA_RT __nullable)result;

/// 重启设备
- (void)cmdRebootDevice;

Source: JL_OTAManager.h

实现代理回调

@protocol JL_OTAManagerDelegate <NSObject>

/// 即将被发送的数据
/// @param data 数据内容
- (void)otaDataSend:(NSData *_Nonnull)data;

@optional
/// 回调设备状态信息
/// @param manager 对象状态
- (void)otaFeatureResult:(JL_OTAManager *_Nonnull)manager;

/// 回调升级状态以及进度等
/// @param result 状态以及进度信息
/// @param progress 进度信息
- (void)otaUpgradeResult:(JL_OTAResult)result Progress:(float)progress;

/// 取消OTA升级
- (void)otaCancel;

@end

Source: JL_OTAManager.h

调用语义:otaDataSend: 中把 data 写入 BLE 特征;otaUpgradeResult:Progress: 中根据 result 更新进度条或展示失败原因(JL_OTAResult 枚举见下文失败模式表);otaFeatureResult: 中检查 manager.otaStatus、manager.otaPartition 等属性决定升级策略。

配置选项

JL_OTAManager 的属性即升级流程的全部可配置项(无独立配置文件):

属性类型默认/初始值说明
mBLE_UUIDNSStringnil(需填入)设备 UUID,开发者必须填写
mBLE_NAMENSStringnil(需填入)设备名称,开发者必须填写
bleOnlyBOOLNO是否仅支持 BLE
bleAddrNSStringnil蓝牙 MAC 地址
mCmdSNuint8_t0指令序号(SDK 内部自增维护)
versionuint16_t0设备版本号
versionFirmwareNSStringnil设备版本信息
otaStatusJL_OtaStatusJL_OtaStatusNormal正常/强制升级,由特性查询填充
otaHeadsetJL_OtaHeadsetJL_OtaHeadsetNO耳机单备份是否强制升级
otaWatchJL_OtaWatchJL_OtaWatchNO手表资源是否强制升级
otaPartitionJL_PartitionJL_PartitionSingle单/双备份,决定是否回连
bootloaderTypeJL_BootLoaderJL_BootLoaderNO是否需要下载 BootLoader
otaReconnectTypeJL_OTAReconnectTypeJL_OTAReconnectTypeUUID回连方式(UUID / MAC)
otaLengthint64_t(只读)0设备通知的升级内容总大小
otaSentuint32_t(只读)0已传输的数据大小
delegateid<JL_OTAManagerDelegate>nil交互回调代理

方法级配置:maxLostCount: 设置最大丢包次数(默认 2);logSendData: 开关发送数据打印(默认关闭)。

API 参考

+ (JL_OTAManager *)getOTAManager

获取全局唯一的 OTA 升级管理对象。init 已被标记为废弃(deprecated("Please use getOTAManager instead.")),禁止自行创建实例。

- (void)noteEntityConnected

BLE 连接并认证完成后调用,告知 SDK 连接就绪。

- (void)noteEntityDisconnected

BLE 断开时调用,告知 SDK 连接已断开(SDK 据此处理 JL_OTAResultDisconnect 等状态)。

- (void)cmdTargetFeature

必选第一步。查询设备 OTA 信息(升级类型、单/双备份、BootLoader 需求、回连方式),结果经 otaFeatureResult: 回调。

- (void)cmdSystemFunction

仅当设备需要挂载外置 Flash 才能正常升级时执行,其他情况无需调用。

- (void)cmdOTAData:(NSData *)data Result:(JL_OTA_RT)result

发起标准 OTA 升级。data 为升级固件数据;result 为升级结果回调块,参数为 (JL_OTAResult result, float progress)。

- (void)cmdOtaDataIIResult:(JL_OTA_RT)result

单备份升级特有。回连成功后再次发起升级(复用已缓存升级数据)。

- (BOOL)cmdOtaIsRelinking

查询 OTA 单备份是否正在回连。

- (void)cmdOTACancelResult:(JL_OTA_RESULT)result

取消升级,result 回调中 status 为 0x00 表示取消成功;取消后 SDK 可能回调 JL_OTAResultCancel。

- (void)cmdRebootDevice / - (void)cmdRebootForceDevice

正常/强制重启设备,用于升级完成后的收尾。

- (void)resetOTAManager

重置 OTA 管理器内部状态,一次完整升级会话结束后调用。

- (void)cmdOtaDataReceive:(NSData *)data

设备端数据入口,业务层收到 BLE 特征数据后原样传入。

- (void)maxLostCount:(int)count

设置最大丢包次数(默认 2),用于弱网场景下的重传策略。

- (void)logSendData:(BOOL)status / + (NSString *)logSDKVersion

调试辅助:打印发送数据、获取 SDK 版本号。

回调块类型:JL_OTA_RT = void (^)(JL_OTAResult result, float progress);JL_OTA_RESULT = void (^)(uint8_t status, uint8_t sn, NSData *data)。

失败模式与边界情况

JL_OTAResult 枚举(JL_OTAManager.h)完整定义了标准升级中可能出现的全部结果码,业务层应逐项映射为 UI 提示:

结果码值含义处理建议
JL_OTAResultSuccess0x00升级成功调用 cmdRebootDevice 收尾
JL_OTAResultFail0x01升级失败展示失败,resetOTAManager
JL_OTAResultDataIsNull0x02升级数据为空检查固件文件读取
JL_OTAResultCommandFail0x03指令失败重试或检查设备状态
JL_OTAResultSeekFail0x04标示偏移查找失败检查固件包合法性
JL_OTAResultInfoFail0x05固件信息错误检查固件包与设备型号匹配
JL_OTAResultLowPower0x06设备电压低提示用户充电后再升级
JL_OTAResultEnterFail0x07未能进入升级模式重新连接后重试
JL_OTAResultUpgrading0x08升级中等待完成
JL_OTAResultReconnect0x09需重连(UUID 方式)单备份回连触发,等待重连
JL_OTAResultReboot0x0a需设备重启等待重启
JL_OTAResultPreparing0x0b准备中等待
JL_OTAResultPrepared0x0f准备完成可发起升级
JL_OTAResultStatusIsUpdating0x10设备已在升级中避免重复发起
JL_OTAResultFailedConnectMore0x11多台设备连接提示用户断开其他设备
JL_OTAResultFailSameSN0xe0SN 多次重复校验失败检查固件/设备 SN
JL_OTAResultCancel0xe1升级取消用户主动取消
JL_OTAResultFailVerification0xf1升级数据校验失败重新获取固件
JL_OTAResultFailCompletely0xf2升级失败重试
JL_OTAResultFailKey0xf3加密 Key 不对检查固件加密配置
JL_OTAResultFailErrorFile0xf4升级文件出错检查固件包完整性
JL_OTAResultFailUboot0xf5uboot 不匹配检查 BootLoader 配置
JL_OTAResultFailLenght0xf6长度出错检查固件包
JL_OTAResultFailFlash0xf7Flash 读写失败设备硬件问题
JL_OTAResultFailCmdTimeout0xf8指令超时结合 maxLostCount: 重试
JL_OTAResultFailSameVersion0xf9相同版本提示用户已是最新版本
JL_OTAResultFailTWSDisconnect0xfaTWS 耳机未连接提示连接双耳
JL_OTAResultFailNotInBin0xfb耳机未在充电仓提示放入充电仓
JL_OTAResultReconnectWithMacAddr0xfc需重连(MAC 方式)按 MAC 回连
JL_OTAResultDisconnect0xfd设备断开检查连接
JL_OTAResultUnknown0xfe未知错误兜底处理

典型边界场景:

  • 单备份回连失败:JL_OTAResultReconnect 之后设备未按时出现,业务层应结合 noteEntityDisconnected 与超时机制提示用户重新靠近设备。
  • 重复升级:设备已在升级中(JL_OTAResultStatusIsUpdating)时再次调用 cmdOTAData: 会被拒绝,应等待当前会话结束。
  • 多设备并发连接:JL_OTAResultFailedConnectMore 明确要求用户手动断开另一台设备,标准流程不支持多设备同时升级。
  • 低电量保护:JL_OTAResultLowPower 表明设备端主动拒绝升级,属于安全设计,避免升级中途断电变砖。

并发与状态一致性

  • 单例模型:JL_OTAManager 通过 getOTAManager 保证全局唯一,天然规避多实例并发升级;但这也意味着同一时刻只能有一个设备处于升级流程。
  • 指令序号:mCmdSN 由 SDK 内部管理,保证请求/应答配对;业务层不应手动修改。
  • 数据喂入顺序:cmdOtaDataReceive: 必须在收到 BLE 数据后及时调用,乱序或丢失会导致校验失败或指令超时(JL_OTAResultFailCmdTimeout)。
  • 状态清理:升级完成或失败后务必调用 resetOTAManager,否则残留状态可能影响下一次 cmdTargetFeature 的结果判断。

性能与运维建议

  • 丢包控制:maxLostCount: 默认 2 次;弱网环境可适当调大,但过大会放大传输时延,需按产品场景权衡。
  • 进度上报:otaUpgradeResult:Progress: 的 progress 与 otaSent/otaLength 均可用于进度条;为避免 UI 频繁刷新,建议业务层做节流(例如每 1% 刷新一次)。
  • 日志:联调阶段开启 logSendData:(发送数据打印)与 logSDKVersion(版本核对),可快速定位是协议问题还是 BLE 通道问题;上线版本建议关闭发送日志以降低开销。
  • 升级时长:大固件(如手表资源)分包传输时间长,期间应保持 BLE 连接稳定、屏幕常亮,必要时提示用户保持 App 在前台。

扩展点

  • 代理协议扩展:JL_OTAManagerDelegate 是唯一的业务扩展接口;新增可选方法不影响现有实现(Objective-C 协议可选方法特性)。
  • 升级类型切换:通过 otaStatus/otaHeadset/otaWatch 可在查询后切换至强制升级等变体流程,标准升级的「查询 → 下发 → 回连 → 重启」骨架对变体同样适用。
  • BootLoader 支持:bootloaderType = JL_BootLoaderYES 时,流程会插入 BootLoader 下载阶段,开发者无需感知细节,仅需在查询结果后按 SDK 指示推进。

相关链接

  • JL_OTAManager.h(核心 API,本页全部接口来源)
  • JL_OTALib.h(SDK 公共头文件聚合)
  • JLBleManager.h(BLE 连接管理,otaManager 属主)
  • JL_ManagerM.h(JL_OTAManager 在设备管理器中的挂载)
  • JL4GUpgradeManager.h(4G 升级流程,见兄弟页面)
Next
自动化测试与批量升级