虽然现在回看这个功能确实挺简单的,不过对于前两天刚学习 IOS 开发(这里的刚学习指的是正式开发以来,之前的涂涂改改不算…)的我来说确实也是实实在在的踩了一些坑。

其实获取网络状态的方案还是有很多的,经过技术调研后我这边选择是先通过 AFNetworking 开源依赖包判断和监听网络变化,然后再通过 IOS CoreTelephony 获取到当前蜂窝网络类型。

好吧,目前找到的博客大部分都是 Object-C 的,所以我还是把这次获取网络类型的踩坑记录下来。

IOS CoreTelephony 官方文档:https://developer.apple.com/documentation/coretelephony/cttelephonynetworkinfo

AFNetworking 依赖 GitHub 地址:https://github.com/AFNetworking/AFNetworking

首先参照 AFNetworking 文档通过 pod 将依赖下载安装到项目。

编辑 Podfile 文件,在项目下添加

……
target 'demo' do
  # Comment the next line if you don't want to use dynamic frameworks
  use_frameworks!

  # Pods for demo
  pod 'AFNetworking', '~> 4.0'

end
……

添加成功后在终端执行 pod install ,下载依赖后打开 demo.xcworkspace 工作空间,这个步骤我相信小伙伴们都是行家了。

安装好 AFNetworking 依赖之后导入依赖并且启动网络监听。

import AFNetworking

func netMonitor() {
if let manager = AFNetworkReachabilityManager.shared() {
            var netStatus = 0
            manager.setReachabilityStatusChange { status in
                switch (status) {
                case AFNetworkReachabilityStatus.notReachable:
                    // 当前是离线状态
                    netStatus = 1
                    break;
                case AFNetworkReachabilityStatus.reachableViaWWAN:
                    // 当前是移动网络
                    netStatus = 2
                    break;
                case AFNetworkReachabilityStatus.reachableViaWiFi:
                    // 当前使用 WIFI 网络
                    netStatus = 3
                    break;
                default:
                    // 其他网络状态
                    netStatus = 0
                    break;
                }
            }
 
            manager.startMonitoring()
        }
}

能看到 AFNetworking 的使用还是挺简单的,就是调用 shared 函数拿到 AFNetworkReachabilityManager 实例后通过 setReachabilityStatusChange 设置网络变化回调函数。最后调用 startMonitoring 函数启动网络状态监听。

当然,通过调用 stopMonitoring 函数还能取消网络变化监听。

现在我们已经能判断出目前使用的是 WIFI 还是蜂窝网络了。但是如果还要判断蜂窝网络类型的话还得用到我们的 CoreTelephony 接口。

import CoreTelephony

func getWWANType() {
                    var netStatus = 0
                    let currentStatus = CTTelephonyNetworkInfo().serviceCurrentRadioAccessTechnology?.values.first
                    switch (currentStatus) {
                    case "CTRadioAccessTechnologyCDMA1x":
                        // 当前网络是 2G
                        netStatus = 5
                        break;
                    case "CTRadioAccessTechnologyCDMAEVDORev0":
                        // 当前网络是 3G
                        netStatus = 6
                        break;
                    case "CTRadioAccessTechnologyCDMAEVDORevA":
                        // 当前网络是 3G
                        netStatus = 6
                        break;
                    case "CTRadioAccessTechnologyCDMAEVDORevB":
                        // 当前网络是 3G
                        netStatus = 6
                        break;
                    case "CTRadioAccessTechnologyeHRPD":
                        // 当前网络是 3G
                        netStatus = 6
                        break;
                    case "CTRadioAccessTechnologyLTE":
                        // 当前网络是 4G
                        netStatus = 7
                        break;
                    case "CTRadioAccessTechnologyNRNSA":
                        // 当前网络是 5G
                        netStatus = 8
                        break;
                    case "CTRadioAccessTechnologyNR":
                        // 当前网络是 5G
                        netStatus = 8
                        break;
                    default:
                        // 其他移动网络类型
                        netStatus = 4
                        break;
                    }
}

导入 CoreTelephony 后,首先实例化 CTTelephonyNetworkInfo 对象,通过 CTTelephonyNetworkInfo 获取 serviceCurrentRadioAccessTechnology 列表中的第一个网络类型判断当前使用的是什么网络类型。

这里拿到的 currentStatus 网络类型是 String 数据类型。相关的网络类型常量可以参考:https://developer.apple.com/documentation/coretelephony/cttelephonynetworkinfo/radio_access_technology_constants

这里我也贴一下根据自己理解后整理的表格(水平有限,仅供参考,如有错误还请指正)。

常量类型网络类型官方描述
CTRadioAccessTechnologyGPRS2G GPRS (又被称为2.5G)The General Packet Radio Service (GPRS) radio access technology.
CTRadioAccessTechnologyEdge2G EDGE (又被称为2.5G 扩展)The Enhanced Data rates for GSM Evolution (EDGE) radio access technology.
CTRadioAccessTechnologyWCDMA3G WCDMAThe Wideband Code Division Multiple Access (WCDMA) radio access technology.
CTRadioAccessTechnologyHSDPA3G EDGE (又被称为3.5G)The High-Speed Downlink Packet Access (HSDPA) radio access technology.
CTRadioAccessTechnologyHSUPA3G HSUPA (又被称为3.75G )The High-Speed Uplink Packet Acess (HSUPA) radio access technology.
CTRadioAccessTechnologyCDMA1x3G CDMA (3G 扩频技术)The Code Division Multiple Access (CDMA) 1x radio access technology.
CTRadioAccessTechnologyCDMAEVDORev03G CDMA (3G 的一种升级方案)The Code Division Multiple Access (CDMA) Evolution-Data Optimized (EV-DO) Rev. 0 radio access technology.
CTRadioAccessTechnologyCDMAEVDORevA3G CDMA (3G 的一种升级方案)The Code Division Multiple Access (CDMA) Evolution-Data Optimized (EV-DO) Rev. A radio access technology.
CTRadioAccessTechnologyCDMAEVDORevB3G CDMA (3G 的一种升级方案)The Code Division Multiple Access (CDMA) Evolution-Data Optimized (EV-DO) Rev. B radio access technology.
CTRadioAccessTechnologyeHRPD3G 的一种升级The Enhanced High Rate Packet Data (eHRPD) radio access technology.
CTRadioAccessTechnologyLTE4G LTEThe Long-Term Evolution (LTE) radio access technology.
CTRadioAccessTechnologyNRNSA5G NRNSAThe 5G New Radio Non-Standalone (NRNSA) radio access technology.
CTRadioAccessTechnologyNR5G NRThe 5G New Radio (NR) radio access technology.

到这里基本上就能实现获取比较全的网络类型了。