跳到主要内容

设计网络框架

问题

如何设计一个 Android 客户端网络框架?

答案

分层架构

核心设计

// API 定义层
interface UserApi {
@GET("users/{id}")
suspend fun getUser(@Path("id") id: String): ApiResponse<User>
}

// 统一响应模型
data class ApiResponse<T>(
val code: Int,
val message: String,
val data: T?
)

// 统一结果封装
sealed class Result<out T> {
data class Success<T>(val data: T) : Result<T>()
data class Error(val code: Int, val message: String) : Result<Nothing>()
data class Exception(val e: Throwable) : Result<Nothing>()
}

Token 自动刷新拦截器

class TokenInterceptor(
private val tokenProvider: TokenProvider
) : Interceptor {

override fun intercept(chain: Interceptor.Chain): Response {
val request = chain.request().newBuilder()
.header("Authorization", "Bearer ${tokenProvider.accessToken}")
.build()

val response = chain.proceed(request)

// 401 时自动刷新 Token 并重试
if (response.code == 401) {
synchronized(this) {
// 双重检查:其他线程可能已经刷新过了
val newToken = tokenProvider.refreshTokenSync()
if (newToken != null) {
response.close()
val retryRequest = request.newBuilder()
.header("Authorization", "Bearer $newToken")
.build()
return chain.proceed(retryRequest)
}
}
}
return response
}
}

网络状态监听

class NetworkMonitor(context: Context) {
private val connectivityManager =
context.getSystemService(Context.CONNECTIVITY_SERVICE) as ConnectivityManager

val isOnline: StateFlow<Boolean> = callbackFlow {
val callback = object : ConnectivityManager.NetworkCallback() {
override fun onAvailable(network: Network) { trySend(true) }
override fun onLost(network: Network) { trySend(false) }
}
connectivityManager.registerDefaultNetworkCallback(callback)
// 初始状态
trySend(connectivityManager.activeNetwork != null)
awaitClose { connectivityManager.unregisterNetworkCallback(callback) }
}.stateIn(CoroutineScope(Dispatchers.IO), SharingStarted.Eagerly, true)
}

设计要点

要点方案
统一错误处理CallAdapter 将 HTTP 异常转为 Result.Error
请求取消协程取消自动取消 OkHttp Call
离线优先OkHttp CacheControl + Room 本地缓存
重试策略OkHttp Interceptor + 指数退避
日志HttpLoggingInterceptor(debug only)

常见面试问题

Q1: Retrofit 和 OkHttp 的关系?

答案

OkHttp 是 HTTP 客户端,负责底层的网络请求(连接池、拦截器、缓存等)。Retrofit 是 OkHttp 之上的声明式 API 框架,通过注解和接口定义来简化请求构建、参数序列化、响应反序列化。Retrofit 内部使用 OkHttp 发起实际的 HTTP 请求。两者是上下层关系,不是替代关系。

相关链接