OkHttp之AndroidPlatform类分析

OkHttp之AndroidPlatform类分析

一、AndroidPlatform 类设计

1. 概述

AndroidPlatform 是 OkHttp 针对 Android 5 到 9(API 21 到 28)平台的特定实现类。它继承自 Platform 类,同时实现 ContextAwarePlatform 接口,为 Android 平台提供定制化的网络连接、SSL 配置和证书管理等功能。

2. 关键属性

  • applicationContext :应用上下文,用于访问 Android 系统服务和资源,实现 ContextAwarePlatform 接口的属性。
  • socketAdapters :用于处理 SSLSocket 的适配器列表,包含多种不同的 SocketAdapter 实例,会根据设备支持情况进行初始化和过滤。

3. 关键方法

  • connectSocket :连接指定的 Socket 到目标地址,针对 Android 8.0(API 26)的特定 bug 进行异常处理。
  • newSSLContext :创建新的 SSLContext 实例,标记该操作是慢操作后调用父类方法。
  • trustManager :从 SSLSocketFactory 中获取 X509TrustManager 实例,遍历 socketAdapters 列表查找匹配适配器。
  • configureTlsExtensions :配置 SSLSocket 的 TLS 扩展,遍历 socketAdapters 列表查找匹配适配器进行配置。
  • getSelectedProtocol :获取 SSLSocket 协商选定的协议,遍历 socketAdapters 列表查找匹配适配器获取协议。
  • isCleartextTrafficPermitted:根据 Android 系统 API 版本判断是否允许明文流量。
  • buildCertificateChainCleaner :尝试使用 AndroidCertificateChainCleaner 构建证书链清理器,失败则调用父类方法。
  • buildTrustRootIndex :尝试通过反射调用 X509TrustManager 的方法构建信任根索引,失败则调用父类方法。

4. 类关系图

classDiagram Platform <|-- AndroidPlatform AndroidPlatform ..|> ContextAwarePlatform AndroidPlatform "1" *-- "n" SocketAdapter : uses AndroidPlatform ..> AndroidCertificateChainCleaner AndroidPlatform ..> NetworkSecurityPolicy AndroidPlatform ..> SSLContext AndroidPlatform ..> X509TrustManager AndroidPlatform ..> SSLSocketFactory AndroidPlatform ..> SSLSocket AndroidPlatform ..> Socket class Platform { <<abstract>> +newSSLContext() +buildCertificateChainCleaner() +buildTrustRootIndex() +trustManager() +configureTlsExtensions() +getSelectedProtocol() +isCleartextTrafficPermitted() +log() } class ContextAwarePlatform { <<interface>> +applicationContext: Context? } class AndroidPlatform { +applicationContext: Context? -socketAdapters: List<SocketAdapter> +connectSocket() +newSSLContext() +trustManager() +configureTlsExtensions() +getSelectedProtocol() +isCleartextTrafficPermitted() +buildCertificateChainCleaner() +buildTrustRootIndex() +getHandshakeServerNames() +log() +CustomTrustRootIndex +buildIfSupported() } class SocketAdapter { <<interface>> +isSupported() +trustManager(sslSocketFactory) +matchesSocket(sslSocket) +matchesSocketFactory(sslSocketFactory) +configureTlsExtensions(sslSocket, hostname, protocols) +getSelectedProtocol(sslSocket) } class AndroidCertificateChainCleaner { +buildIfSupported() } class NetworkSecurityPolicy { +getInstance() +isCleartextTrafficPermitted() }

5. 平台选择流程图

flowchart TD A[Platform.buildPlatform] --> B{平台类型?} B -->|JVM| C[JvmPlatformRegistry.findPlatform] B -->|Android| D[AndroidPlatformRegistry.findPlatform] C --> C1{Conscrypt可用?} C1 -->|是| C2[ConscryptPlatform] C1 -->|否| C3{OpenJSSE可用?} C3 -->|是| C4[OpenJSSEPlatform] C3 -->|否| C5{BouncyCastle可用?} C5 -->|是| C6[BouncyCastlePlatform] C5 -->|否| C7{JDK 9+或JDK 8 build 252+?} C7 -->|是| C8[Jdk9Platform] C7 -->|否| C9{JDK 8?} C9 -->|是| C10[Jdk8WithJettyBootPlatform] C9 -->|否| C11[默认Platform] D --> D1{Android 10+?} D1 -->|是| D2[Android10Platform] D1 -->|否| D3{Android 5 - 9?} D3 -->|是| D4[AndroidPlatform] D4 --> D41{ConscryptSocketAdapter支持?} D41 -->|是| D42[使用ConscryptSocketAdapter] D41 -->|否| D43{BouncyCastleSocketAdapter支持?} D43 -->|是| D44[使用BouncyCastleSocketAdapter] D43 -->|否| D45{AndroidSocketAdapter支持?} D45 -->|是| D46[使用AndroidSocketAdapter] D45 -->|否| D47[使用默认SocketAdapter处理] D3 -->|否| D5{API版本=0?} D5 -->|是| D6[Jdk9Platform或默认Platform] D5 -->|否| D7[抛出异常]

二、SocketAdapter 扩展设计

1. 概述

SocketAdapter 是一个接口,旨在为不同的 SSLSocket 实现提供适配能力。通过实现该接口,开发者能轻松添加新的 SSLSocket 适配逻辑,而不影响现有代码。

2. 关键方法

  • isSupported() :判断当前平台是否支持该 SocketAdapter 实现。
  • trustManager(sslSocketFactory) :从 SSLSocketFactory 中获取 X509TrustManager 实例,默认返回 null。
  • matchesSocket(sslSocket) :判断给定的 SSLSocket 是否与当前 SocketAdapter 匹配。
  • matchesSocketFactory(sslSocketFactory) :判断给定的 SSLSocketFactory 是否与当前 SocketAdapter 匹配,默认返回 false。
  • configureTlsExtensions(sslSocket, hostname, protocols) :配置 SSLSocket 的 TLS 扩展。
  • getSelectedProtocol(sslSocket) :获取 SSLSocket 协商选定的协议。

3. 常见实现类

  • AndroidSocketAdapter :基于现代反射的 Socket 适配器,适用于 Conscrypt 类的 SSLSocket。
  • Android10SocketAdapter :适用于 Android Q(API 级别 29)及以上版本的简单非反射 Socket 适配器。
  • ConscryptSocketAdapter :当 Conscrypt 作为应用依赖直接引入时,使用的简单非反射 Socket 适配器。
  • BouncyCastleSocketAdapter :适用于 Bouncy Castle 的简单非反射 Socket 适配器。

三、SocketAdapter 泛化分析

1. 泛化概念

SocketAdapter 接口的设计具备良好的泛化能力,不同的实现类可根据具体的 SSLSocket 实现(如 Conscrypt、Bouncy Castle 等)提供适配逻辑。这种设计使得 SocketAdapter 能够灵活应对多种 SSLSocket 实现,降低了代码的耦合度,提高了可扩展性。

2. 泛化类关系图

classDiagram SocketAdapter <|-- AndroidSocketAdapter SocketAdapter <|-- Android10SocketAdapter SocketAdapter <|-- ConscryptSocketAdapter SocketAdapter <|-- BouncyCastleSocketAdapter SocketAdapter <|-- CustomSocketAdapter class SocketAdapter { <<interface>> +isSupported() +trustManager(sslSocketFactory) +matchesSocket(sslSocket) +matchesSocketFactory(sslSocketFactory) +configureTlsExtensions(sslSocket, hostname, protocols) +getSelectedProtocol(sslSocket) } class AndroidSocketAdapter { +isSupported() +trustManager(sslSocketFactory) +matchesSocket(sslSocket) +matchesSocketFactory(sslSocketFactory) +configureTlsExtensions(sslSocket, hostname, protocols) +getSelectedProtocol(sslSocket) } class Android10SocketAdapter { +isSupported() +trustManager(sslSocketFactory) +matchesSocket(sslSocket) +matchesSocketFactory(sslSocketFactory) +configureTlsExtensions(sslSocket, hostname, protocols) +getSelectedProtocol(sslSocket) } class ConscryptSocketAdapter { +isSupported() +trustManager(sslSocketFactory) +matchesSocket(sslSocket) +matchesSocketFactory(sslSocketFactory) +configureTlsExtensions(sslSocket, hostname, protocols) +getSelectedProtocol(sslSocket) } class BouncyCastleSocketAdapter { +isSupported() +trustManager(sslSocketFactory) +matchesSocket(sslSocket) +matchesSocketFactory(sslSocketFactory) +configureTlsExtensions(sslSocket, hostname, protocols) +getSelectedProtocol(sslSocket) } class CustomSocketAdapter { +isSupported() +trustManager(sslSocketFactory) +matchesSocket(sslSocket) +matchesSocketFactory(sslSocketFactory) +configureTlsExtensions(sslSocket, hostname, protocols) +getSelectedProtocol(sslSocket) }

从图中可以看出,SocketAdapter 作为接口,多个具体的适配器类实现了该接口。CustomSocketAdapter 表示开发者可以自定义的适配器类,体现了 SocketAdapter 接口的泛化能力,开发者能根据需求添加新的适配器实现。

四、AndroidPlatform 与 SocketAdapter 的关系

1. 依赖关系

AndroidPlatform 依赖 SocketAdapter 来处理 SSLSocket 相关操作。AndroidPlatform 持有一个 socketAdapters 列表,在进行 SSLSocket 相关操作时,会遍历该列表,找到匹配的 SocketAdapter 并调用其方法。

2. 协作流程

以 trustManager 方法为例
sequenceDiagram participant Client participant AndroidPlatform participant SocketAdapter Client->>AndroidPlatform: trustManager(sslSocketFactory) AndroidPlatform->>AndroidPlatform: Iterate socketAdapters loop For each SocketAdapter AndroidPlatform->>SocketAdapter: matchesSocketFactory(sslSocketFactory) alt Match found SocketAdapter-->>AndroidPlatform: true AndroidPlatform->>SocketAdapter: trustManager(sslSocketFactory) SocketAdapter-->>AndroidPlatform: X509TrustManager AndroidPlatform-->>Client: X509TrustManager else No match SocketAdapter-->>AndroidPlatform: false end end alt No match found AndroidPlatform-->>Client: null end
以 configureTlsExtensions 方法为例
sequenceDiagram participant Client participant AndroidPlatform participant SocketAdapter Client->>AndroidPlatform: configureTlsExtensions(sslSocket, hostname, protocols) AndroidPlatform->>AndroidPlatform: Iterate socketAdapters loop For each SocketAdapter AndroidPlatform->>SocketAdapter: matchesSocket(sslSocket) alt Match found SocketAdapter-->>AndroidPlatform: true AndroidPlatform->>SocketAdapter: configureTlsExtensions(sslSocket, hostname, protocols) SocketAdapter-->>AndroidPlatform: Operation completed AndroidPlatform-->>Client: Operation completed else No match SocketAdapter-->>AndroidPlatform: false end end alt No match found AndroidPlatform-->>Client: No suitable adapter found end

AndroidPlatform 通过 SocketAdapter 泛化最终实现了与 JVM 平台类似的降级策略,下面从多个方面详细分析:

降级策略概念

降级策略通常是指在系统运行过程中,当某些高级功能无法正常使用或者资源不足时,系统会自动切换到次优方案,以保证基本功能的正常运行。在网络通信场景中,可能表现为当无法使用最新的安全协议或加密算法时,退而使用较旧但仍可用的协议或算法。

AndroidPlatform 与 SocketAdapter 实现降级策略的方式

1. 多 SocketAdapter 实现

SocketAdapter 是一个接口,有多种实现类,如 AndroidSocketAdapter、ConscryptSocketAdapter、BouncyCastleSocketAdapter 等。每个实现类对应不同的 SSLSocket 实现或不同的 Android 平台版本,这就为降级提供了多种备选方案。

classDiagram SocketAdapter <|-- AndroidSocketAdapter SocketAdapter <|-- ConscryptSocketAdapter SocketAdapter <|-- BouncyCastleSocketAdapter SocketAdapter <|-- Android10SocketAdapter class SocketAdapter { <<interface>> +isSupported() +trustManager(sslSocketFactory) +matchesSocket(sslSocket) +matchesSocketFactory(sslSocketFactory) +configureTlsExtensions(sslSocket, hostname, protocols) +getSelectedProtocol(sslSocket) }

2. 动态选择适配器

AndroidPlatform 持有一个 socketAdapters 列表,在进行 SSLSocket 相关操作时,会遍历该列表,依次调用每个 SocketAdapter 的 isSupported() 和 matchesSocket() 等方法,找到第一个匹配且支持的 SocketAdapter 来处理操作。如果当前的适配器不支持,就尝试下一个,直到找到合适的适配器或者遍历完所有适配器。

sequenceDiagram participant Client participant AndroidPlatform participant Adapter1 participant Adapter2 participant Adapter3 Client->>AndroidPlatform: configureTlsExtensions(sslSocket, ...) AndroidPlatform->>Adapter1: isSupported() Adapter1-->>AndroidPlatform: false AndroidPlatform->>Adapter2: isSupported() Adapter2-->>AndroidPlatform: true AndroidPlatform->>Adapter2: matchesSocket(sslSocket) Adapter2-->>AndroidPlatform: true AndroidPlatform->>Adapter2: configureTlsExtensions(sslSocket, ...) Adapter2-->>AndroidPlatform: Success AndroidPlatform-->>Client: Success

3. 降级效果

当系统环境发生变化,比如 Android 版本升级、依赖库缺失等,导致某些 SocketAdapter 不再支持时,AndroidPlatform 会自动选择其他可用的 SocketAdapter,从而保证网络通信功能的正常运行。这与 JVM 平台的降级策略类似,JVM 平台在遇到安全协议不支持、证书验证失败等问题时,也会尝试使用其他方案来保证通信的基本功能。

与 JVM 平台降级策略的相似性

  • 多方案选择 :JVM 平台也有多种安全协议、加密算法和网络库的实现可供选择。当首选方案不可用时,会尝试其他方案。例如,当 TLS 1.3 不可用时,会降级到 TLS 1.2。AndroidPlatform 同样通过 SocketAdapter 提供了多种适配方案,根据实际情况选择合适的适配器。
  • 自动降级 :JVM 平台和 AndroidPlatform 都能自动检测环境变化,在发现当前方案不可行时,自动切换到备用方案,无需人工干预。

综上所述,AndroidPlatform 通过 SocketAdapter 泛化实现了与 JVM 平台类似的降级策略,提高了系统的健壮性和兼容性。

五、总结

AndroidPlatform 通过组合多个 SocketAdapter 实例,实现了对不同 SSLSocket 实现的灵活支持。SocketAdapter 接口的泛化设计使得新的 SSLSocket 适配逻辑可以方便地扩展,提高了代码的可维护性和可扩展性。这种设计模式符合开闭原则,对扩展开放,对修改关闭。开发者可以根据具体需求实现新的 SocketAdapter 类,以支持更多类型的 SSLSocket 实现。

相关推荐
stevenzqzq23 分钟前
mvi的理解
android·compose
脚踏实地,坚持不懈!43 分钟前
Android 电池健康度检测全流程(驱动 → 内核 → HAL → Framework)
android·linux
恋猫de小郭1 小时前
Genkit Dart 1.0 发布,Flutter 原生的 AI Agent 终于完整了
android·前端·flutter
迪康妍妍1 小时前
终端安全实战:用迪康终端安全管理系统实现U盘四分档管控与全量审计
android·运维·网络·安全·电脑
JackLam1 小时前
mobile-use 使用与接入第三方 LLM 网关完整指南OC
android·ai·mobile use
snotJam1 小时前
关于Uniapp的Android自定义基座使用
android·uni-app
TST-魚爷2 小时前
易视讯会议摄像头电视安装教程
android·电脑·钉钉·腾讯会议·zoom会议
墨天梦11 小时前
B17_LifecycleLiveData与Flow
android·kotlin
_祝你今天愉快12 小时前
UI核心 - 绘制流程(测量、布局、绘制)
android
冬奇Lab13 小时前
LLM 驱动的自动化测试系列(07):移动端自动化(三)——Mobile-Agent-v3 与自研 GUI-Owl 模型路线
android·人工智能·测试