当前位置: 首页 > news >正文

网络状态监听:监听网络连接类型(WiFi/5G)变化(41)

在鸿蒙(HarmonyOS)开发中,实时监听网络状态是保障应用体验的核心能力。当用户在 Wi-Fi、4G、5G 等网络间切换时,应用需及时响应(如提示网络变化、调整下载并发数),避免因网络波动导致卡顿或流量浪费。

鸿蒙通过@kit.NetworkKit中的@ohos.net.connection模块提供标准化的网络状态监听接口。以下是完整的实战开发指南:

一、 环境准备与权限配置

网络状态监听属于敏感操作,必须在module.json5中声明相关权限:

"requestPermissions": [ { "name": "ohos.permission.INTERNET" }, { "name": "ohos.permission.GET_NETWORK_INFO" } ]

二、 核心代码:网络状态监听与类型识别

通过createNetConnection创建网络连接对象,注册各类网络变化事件,并在回调中解析当前网络类型。

import { connection } from '@kit.NetworkKit'; import { BusinessError } from '@kit.BasicServicesKit'; @Entry @Component struct NetworkMonitorDemo { private netConnection: connection.NetConnection = connection.createNetConnection(); aboutToAppear() { this.startNetworkMonitor(); } private startNetworkMonitor() { // 1. 注册网络订阅(必须先注册,才能接收后续事件) this.netConnection.register((error: BusinessError) => { if (error) { console.error('网络注册监听失败:', JSON.stringify(error)); return; } console.info('网络注册监听成功'); }); // 2. 监听网络可用事件 this.netConnection.on('netAvailable', (data: connection.NetHandle) => { console.info(`网络可用, netId: ${data.netId}`); }); // 3. 监听网络能力变化(核心:用于识别网络类型切换) this.netConnection.on('netCapabilitiesChange', (data: connection.NetCapabilityInfo) => { const bearerTypes = data.netCap?.bearerTypes; const networkCaps = data.netCap?.networkCap; // 解析网络类型(Wi-Fi / 蜂窝网络) if (bearerTypes?.includes(connection.NetBearType.BEARER_WIFI)) { console.info('当前网络类型: Wi-Fi'); } else if (bearerTypes?.includes(connection.NetBearType.BEARER_CELLULAR)) { console.info('当前网络类型: 蜂窝网络 (4G/5G)'); } // 解析网络能力(如是否真正可访问互联网) if (networkCaps?.includes(connection.NetCap.NET_CAPABILITY_VALIDATED)) { console.info('网络已验证,可正常访问互联网'); } }); // 4. 监听网络丢失事件(如断开 Wi-Fi 且无蜂窝网络) this.netConnection.on('netLost', (data: connection.NetHandle) => { console.warn(`网络丢失, netId: ${data.netId}`); }); // 5. 监听网络不可用事件(如连上了 Wi-Fi 但无法上网) this.netConnection.on('netUnavailable', () => { console.warn('当前网络不可用'); }); } aboutToDisappear() { // 退出页面时取消订阅,防止内存泄漏 this.netConnection.unregister((error: BusinessError) => { if (error) { console.error('取消网络监听失败:', JSON.stringify(error)); } }); } build() { Column({ space: 20 }) { Text('网络状态监听演示') .fontSize(24) .fontWeight(FontWeight.Bold) } .width('100%') .height('100%') .justifyContent(FlexAlign.Center) } }

三、 进阶:结合状态管理实现 UI 联动

在实际业务中,网络状态通常需要全局共享并驱动 UI 更新。推荐使用AppStorage结合@StorageProp@Watch实现响应式联动。

// 1. 在工具类或全局监听中,将状态写入 AppStorage this.netConnection.on('netCapabilitiesChange', (data) => { let isNetAvailable = data.netCap?.networkCap?.includes(connection.NetCap.NET_CAPABILITY_VALIDATED); AppStorage.setOrCreate('isNetAvailable', isNetAvailable ?? false); }); // 2. 在 UI 组件中监听状态变化 @StorageProp('isNetAvailable') @Watch('onNetworkChanged') isNetAvailable: boolean = true; onNetworkChanged() { if (this.isNetAvailable) { console.info('网络已恢复,执行重新连接/恢复下载逻辑'); } else { console.warn('网络已断开,暂停下载并提示用户'); } }

开发建议与注意事项

  1. 区分netLostnetUnavailable
    • netLost:网络严重中断或正常断开(如手动关闭 Wi-Fi)。
    • netUnavailable:网络已连接但不可用(如连上了 Wi-Fi 但路由器未连外网,图标显示感叹号)。
  2. 网络切换的事件触发顺序:当设备从 Wi-Fi 切换到蜂窝网络时,系统会先触发netLost(Wi-Fi 丢失),再触发netAvailable(蜂窝网络可用)。在开发重连逻辑时需注意时序。
  3. 低功耗设计:鸿蒙网络监听采用事件订阅机制,仅在状态变化时唤醒应用回调,避免了持续轮询带来的高耗电问题。
  4. 不支持主动切换:系统原生能力仅支持通过回调“感知”网络切换,不支持应用主动进行网络切换。

四、 精准识别蜂窝网络代际(5G/4G/3G/2G)

基础的connection模块只能区分出当前是否处于“蜂窝网络”状态。如果需要精准识别当前是 5G、4G 还是 3G,需要结合@ohos.telephony.radio模块获取信号信息。

核心代码示例:

import { connection } from '@kit.NetworkKit'; import { radio } from '@kit.TelephonyKit'; // 当监听到当前网络为蜂窝网络时,进一步获取具体代际 async function getCellularGeneration() { try { // 获取当前设备的信号信息列表(支持双卡) const signalInfos = await radio.getSignalInformation(); if (signalInfos && signalInfos.length > 0) { // 获取主卡的信号类型 const signalType = signalInfos[0].signalType; switch (signalType) { case radio.NetworkType.NETWORK_TYPE_NR: console.info('当前蜂窝网络: 5G'); break; case radio.NetworkType.NETWORK_TYPE_LTE: console.info('当前蜂窝网络: 4G'); break; case radio.NetworkType.NETWORK_TYPE_WCDMA: case radio.NetworkType.NETWORK_TYPE_TDSCDMA: console.info('当前蜂窝网络: 3G'); break; default: console.info('当前蜂窝网络: 2G/未知'); break; } } } catch (err) { console.error('获取蜂窝网络代际失败'); } }

五、 弱网状态感知(ASCF 框架)

在音视频通话、实时游戏等对网络延迟敏感的场景中,仅知道“网络是否连接”是不够的,还需要感知当前是否处于“弱网”状态。鸿蒙 ASCF 框架提供了专门的弱网监听接口。

核心代码示例:

import { has } from '@kit.ASCFKit'; // 假设基于 ASCF 框架 // 监听弱网状态变化 has.onNetworkWeakChange((res) => { console.info(`弱网状态变更: ${res.weakNet}, 当前网络类型: ${res.networkType}`); if (res.weakNet) { // 弱网策略:降低视频码率、减少心跳频率、暂停后台预加载等 console.warn('检测到弱网,正在切换至低画质模式...'); } else { // 网络恢复:恢复正常策略 console.info('网络状况良好,恢复标准画质'); } }); // 在生命周期中取消监听 has.offNetworkWeakChange();

六、 多网并发与连接迁移(Network Boost Kit)

对于大型文件下载、直播推流等高吞吐业务,鸿蒙提供了 Network Boost Kit,允许应用感知多网并发状态(例如同时使用 Wi-Fi 和蜂窝网络),从而制定更优的数据传输策略。

核心代码示例:

import { netHandover } from '@kit.NetworkBoostKit'; import { BusinessError } from '@kit.BasicServicesKit'; // 订阅多网状态信息变化 try { netHandover.on('multiPathStateChange', (data: netHandover.MultiPathStateInfo) => { console.info("多网状态变化: " + JSON.stringify(data)); // 根据多网状态调整并发下载线程数或传输策略 }); } catch (err) { console.error('监听多网状态失败: ' + (err as BusinessError).message); } // 业务结束时取消订阅 try { netHandover.off('multiPathStateChange'); } catch (err) { console.error('取消多网状态监听失败: ' + (err as BusinessError).message); }

七、 网络质量量化监控(延迟、带宽、信号强度)

在音视频通话、实时游戏等对网络延迟极度敏感的场景中,除了感知“弱网”,还需要获取具体的网络质量指标(如 RTT 延迟、上下行带宽、信号强度 RSRP)。由于系统可能没有直接提供实时的质量变化监听,通常采用定时主动探测的方式来实现。

核心代码示例:

import { connection } from '@kit.NetConnectionKit'; // 定义网络质量模型 interface NetworkQuality { level: 'EXCELLENT' | 'GOOD' | 'FAIR' | 'POOR' | 'UNKNOWN'; signalStrength: number; latency: number; bandwidth: number; } // 定时检测网络质量 async function measureNetworkQuality(): Promise<NetworkQuality> { const startTime = Date.now(); try { // 通过发起轻量级请求来测量延迟(RTT) await fetch('https://connectivitycheck.gstatic.com/generate_204', { timeout: 5000 }); const latency = Date.now() - startTime; // 根据延迟评估质量等级 let level: NetworkQuality['level'] = 'UNKNOWN'; if (latency < 100) level = 'EXCELLENT'; else if (latency < 300) level = 'GOOD'; else if (latency < 800) level = 'FAIR'; else level = 'POOR'; return { level, signalStrength: 0, latency, bandwidth: 0 }; } catch (err) { return { level: 'POOR', signalStrength: 0, latency: -1, bandwidth: 0 }; } } // 每 5 秒执行一次质量评估 setInterval(async () => { const quality = await measureNetworkQuality(); console.info(`当前网络质量: ${quality.level}, 延迟: ${quality.latency}ms`); }, 5000);

八、 智能 DNS 解析

在多网络并存或复杂网络环境下,直接使用域名发起请求可能会遇到 DNS 劫持或解析缓慢的问题。鸿蒙提供了系统级的智能 DNS 解析接口,可以直接获取目标域名的 IP 地址列表,便于应用层自行管理连接。

核心代码示例:

import { connection } from '@kit.NetworkKit'; async function resolveDomain() { try { const addresses = await connection.getAddressesByName("www.example.com"); console.info("解析到的 IP 地址列表:", addresses.join(', ')); // 业务层可使用解析出的 IP 直接建立连接,绕过系统默认 DNS } catch (err) { console.error("DNS 解析失败:", (err as BusinessError).message); } }

九、 底层网络状态强制修正

在某些极端场景下(如底层网卡驱动异常、代理软件干扰),应用内部记录的网络状态可能与系统网络管理器不一致。鸿蒙提供了强制报告网络状态的接口,用于纠正系统的误判。

核心代码示例:

import { connection } from '@kit.NetworkKit'; // 当发现网络状态异常且确认当前网络不可用时,强制向系统报告网络断开 function forceReportDisconnect(badNetHandle: connection.NetHandle) { connection.reportNetDisconnected(badNetHandle); console.warn('已强制报告网络断开'); } // 当确认某个网络句柄实际可用,但系统未识别时,强制报告连接 function forceReportConnect(goodNetHandle: connection.NetHandle) { connection.reportNetConnected(goodNetHandle); console.info('已强制报告网络连接'); }

底层通信资源管控与避坑

在复杂的网络切换过程中,底层通信资源的管理至关重要,处理不当极易导致内存泄漏或请求异常。

  1. Socket 资源强制释放:当监听到网络切换(如 Wi-Fi 切 5G)或网络丢失时,必须主动关闭旧的 Socket 连接。旧的网络句柄在新的网络环境下已失效,继续持有会导致资源泄漏。
  2. 推荐使用高级通信套件:在多网络频繁切换的场景下,强烈建议使用@kit.RemoteCommunicationKit替代原生的 HTTP 模块,它内置了更好的连接池管理和网络异常恢复机制。
  3. 紧急情况下的状态修正:当遇到应用内部记录的网络状态与系统管理器不一致时(例如应用认为已断网,但系统实际可用),可以调用connection.reportNetDisconnected(badNetHandle)connection.reportNetConnected(goodNetHandle)强制向系统报告网络状态。
  4. 生命周期严格绑定:网络监听会持续占用系统资源。务必在EntryAbilityonCreate中开启订阅,在onWindowStageDestroy中关闭订阅,防止应用进入后台后仍进行不必要的状态回调。
http://www.cnnetsun.cn/news/2952425.html

相关文章:

  • 洛雪音乐音源库:5步配置指南与多平台音乐资源整合方案
  • ZigBee ZCL属性报告机制:从轮询到事件驱动的低功耗物联网通信
  • W223奔驰S级/迈巴赫改装避坑指南!2026年版内行干货
  • Bodymovin扩展面板:专业级AE动画导出与Lottie工作流完全指南
  • 计算机视觉算法:实时场景重建与SLAM技术及多传感器融合感知算法(下)
  • 列式存储核心原理:手写简易列式引擎、压缩编码(Delta_ZSTD)、投影下推,对比行存分析查询性能差异
  • 如何将普通汽车升级为智能座驾:openpilot完整指南
  • 247.FPGA中HR bank HP bank SRCC MRCC
  • (精选题)拒绝死记硬背!从20道真题拆解到精通TCP/UDP:计算机网络传输层终极指南(附源码与避坑指南)
  • Hi7200:6-65V输入,外置MOS可驱动25A,支持PWM/模拟/切光三模式调光同步降压LED恒流驱动器
  • 2026年6月,GPT Pro 和 Codex 充值问题越来越明显了
  • 如何快速上手CodeLite:跨平台IDE完整安装与配置指南
  • ZigBee 3.0网络参数配置实战:从核心原理到工程调优
  • ArcGIS城市水文脉络解析——以深圳为例
  • E7Helper:第七史诗自动化脚本的3个实用功能与配置指南
  • 高效解密RPG Maker加密档案:专业工具深度解析与实战指南
  • CodeWarrior IDE 5.7实战:从控制台项目创建到高效代码编辑与导航
  • 云专线技术解析:从原理到实践,构建企业混合云高速通道
  • Llama 3.1 405B微调实战:大模型工业化落地的关键路径
  • 手把手实战:CANN ops-transformer算子库在昇腾NPU上加速Transformer大模型计算
  • Adobe-GenP 3.0终极指南:5分钟解锁Adobe全系列软件完整功能
  • CodeWarrior IDE 5.7 菜单系统详解:从核心操作到嵌入式开发实战
  • 苏州晟雅泰电子:关于CXDB5CCBM-EA-A这个物料的应用领域剖析
  • Oracle EXPLAIN PLAN
  • YOLOv8【第十七章:前沿演进与跨界融合篇·第5节】RT-DETR:基于 Transformer 的实时检测器与 YOLOv8 的全方位对比!
  • WaveTools鸣潮工具箱:5分钟搞定抽卡记录同步与画质优化
  • IDEA 创建 Java 项目 负载均衡 获取 Nacos 服务地址
  • 机器人终于会主动找你了!触发器实战,每天8点自动推送新闻
  • 揭秘终极游戏模组管理:XXMI启动器深度解析与实战指南
  • Godot卡牌游戏框架终极指南:快速构建专业级卡牌游戏的完整解决方案