Kotlin 实现 Android 网络状态检测工具类

以下是一个完整的 Android Kotlin 网络连接检测工具类:

  1. 添加权限

首先在 AndroidManifest.xml 中添加网络权限:

xml 复制代码
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
<uses-permission android:name="android.permission.ACCESS_WIFI_STATE" />
  1. 网络连接工具类
kotlin 复制代码
import android.content.Context
import android.net.ConnectivityManager
import android.net.Network
import android.net.NetworkCapabilities
import android.net.NetworkRequest
import android.os.Build
import kotlinx.coroutines.flow.MutableStateFlow
import kotlinx.coroutines.flow.StateFlow

/**
 * 网络连接状态工具类
 * 支持实时监听网络状态变化
 */
object NetworkUtils {

    private var connectivityManager: ConnectivityManager? = null
    
    // 网络状态流,可以观察网络状态变化
    private val _networkState = MutableStateFlow(false)
    val networkState: StateFlow<Boolean> = _networkState

    /**
     * 初始化工具类
     */
    fun initialize(context: Context) {
        connectivityManager = context.getSystemService(Context.CONNECTIVITY_SERVICE) as? ConnectivityManager
        updateNetworkState(context)
        registerNetworkCallback(context)
    }

    /**
     * 检查是否连接网络
     */
    fun isNetworkConnected(context: Context): Boolean {
        return try {
            val cm = connectivityManager ?: context.getSystemService(Context.CONNECTIVITY_SERVICE) as ConnectivityManager
            
            if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
                val network = cm.activeNetwork
                val capabilities = cm.getNetworkCapabilities(network)
                capabilities != null && (
                    capabilities.hasTransport(NetworkCapabilities.TRANSPORT_WIFI) ||
                    capabilities.hasTransport(NetworkCapabilities.TRANSPORT_CELLULAR) ||
                    capabilities.hasTransport(NetworkCapabilities.TRANSPORT_ETHERNET)
                )
            } else {
                @Suppress("DEPRECATION")
                val networkInfo = cm.activeNetworkInfo
                networkInfo != null && networkInfo.isConnected
            }
        } catch (e: Exception) {
            e.printStackTrace()
            false
        }
    }

    /**
     * 检查是否是 WiFi 连接
     */
    fun isWifiConnected(context: Context): Boolean {
        return try {
            val cm = connectivityManager ?: context.getSystemService(Context.CONNECTIVITY_SERVICE) as ConnectivityManager
            
            if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
                val network = cm.activeNetwork
                val capabilities = cm.getNetworkCapabilities(network)
                capabilities?.hasTransport(NetworkCapabilities.TRANSPORT_WIFI) == true
            } else {
                @Suppress("DEPRECATION")
                val networkInfo = cm.activeNetworkInfo
                networkInfo != null && networkInfo.isConnected && networkInfo.type == ConnectivityManager.TYPE_WIFI
            }
        } catch (e: Exception) {
            e.printStackTrace()
            false
        }
    }

    /**
     * 检查是否是移动数据连接
     */
    fun isMobileDataConnected(context: Context): Boolean {
        return try {
            val cm = connectivityManager ?: context.getSystemService(Context.CONNECTIVITY_SERVICE) as ConnectivityManager
            
            if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
                val network = cm.activeNetwork
                val capabilities = cm.getNetworkCapabilities(network)
                capabilities?.hasTransport(NetworkCapabilities.TRANSPORT_CELLULAR) == true
            } else {
                @Suppress("DEPRECATION")
                val networkInfo = cm.activeNetworkInfo
                networkInfo != null && networkInfo.isConnected && networkInfo.type == ConnectivityManager.TYPE_MOBILE
            }
        } catch (e: Exception) {
            e.printStackTrace()
            false
        }
    }

    /**
     * 获取网络类型
     */
    fun getNetworkType(context: Context): String {
        return when {
            isWifiConnected(context) -> "WiFi"
            isMobileDataConnected(context) -> "Mobile"
            else -> "No Network"
        }
    }

    /**
     * 注册网络状态监听
     */
    private fun registerNetworkCallback(context: Context) {
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
            val cm = connectivityManager ?: return
            
            val networkRequest = NetworkRequest.Builder()
                .addTransportType(NetworkCapabilities.TRANSPORT_WIFI)
                .addTransportType(NetworkCapabilities.TRANSPORT_CELLULAR)
                .addTransportType(NetworkCapabilities.TRANSPORT_ETHERNET)
                .build()

            cm.registerNetworkCallback(networkRequest, object : ConnectivityManager.NetworkCallback() {
                override fun onAvailable(network: Network) {
                    _networkState.value = true
                }

                override fun onLost(network: Network) {
                    _networkState.value = false
                }

                override fun onUnavailable() {
                    _networkState.value = false
                }
            })
        }
    }

    /**
     * 更新网络状态
     */
    private fun updateNetworkState(context: Context) {
        _networkState.value = isNetworkConnected(context)
    }
}
  1. 扩展函数
kotlin 复制代码
/**
 * Context 的扩展函数,简化调用
 */
fun Context.isNetworkConnected(): Boolean {
    return NetworkUtils.isNetworkConnected(this)
}

fun Context.isWifiConnected(): Boolean {
    return NetworkUtils.isWifiConnected(this)
}

fun Context.isMobileDataConnected(): Boolean {
    return NetworkUtils.isMobileDataConnected(this)
}

fun Context.getNetworkType(): String {
    return NetworkUtils.getNetworkType(this)
}
  1. 使用示例

在 Application 中初始化:

kotlin 复制代码
class MyApplication : Application() {
    override fun onCreate() {
        super.onCreate()
        NetworkUtils.initialize(this)
    }
}

在 Activity/Fragment 中使用:

kotlin 复制代码
class MainActivity : AppCompatActivity() {

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)

        // 基本使用
        checkNetworkStatus()
        
        // 观察网络状态变化
        observeNetworkState()
    }

    /**
     * 检查当前网络状态
     */
    private fun checkNetworkStatus() {
        if (isNetworkConnected()) {
            val networkType = getNetworkType()
            Toast.makeText(this, "网络已连接 - $networkType", Toast.LENGTH_SHORT).show()
        } else {
            Toast.makeText(this, "网络未连接", Toast.LENGTH_SHORT).show()
        }

        // 或者使用工具类直接调用
        if (NetworkUtils.isNetworkConnected(this)) {
            // 执行网络请求
        }
    }

    /**
     * 观察网络状态变化
     */
    private fun observeNetworkState() {
        lifecycleScope.launch {
            NetworkUtils.networkState.collect { isConnected ->
                if (isConnected) {
                    // 网络恢复
                    showNetworkRestored()
                } else {
                    // 网络断开
                    showNetworkLost()
                }
            }
        }
    }

    private fun showNetworkRestored() {
        // 显示网络恢复提示
        Snackbar.make(findViewById(android.R.id.content), 
            "网络已恢复", Snackbar.LENGTH_SHORT).show()
    }

    private fun showNetworkLost() {
        // 显示网络断开提示
        Snackbar.make(findViewById(android.R.id.content), 
            "网络连接已断开", Snackbar.LENGTH_LONG).show()
    }
}

在网络请求前检查:

kotlin 复制代码
class UserRepository(private val context: Context) {
    
    suspend fun fetchUserData(): Result<User> {
        // 在发起网络请求前检查网络
        if (!context.isNetworkConnected()) {
            return Result.failure(IOException("网络未连接"))
        }
        
        return try {
            // 执行网络请求
            val response = apiService.getUser()
            Result.success(response)
        } catch (e: Exception) {
            Result.failure(e)
        }
    }
}
  1. 高级功能 - 网络状态监听器

如果需要更详细的回调,可以添加监听器:

kotlin 复制代码
interface NetworkStateListener {
    fun onNetworkAvailable(networkType: String)
    fun onNetworkLost()
    fun onNetworkTypeChanged(networkType: String)
}

class AdvancedNetworkMonitor(private val context: Context) {
    private val listeners = mutableSetOf<NetworkStateListener>()
    private var lastNetworkType = ""
    
    init {
        observeNetworkState()
    }
    
    private fun observeNetworkState() {
        lifecycleScope.launch {
            NetworkUtils.networkState.collect { isConnected ->
                val currentType = context.getNetworkType()
                
                if (isConnected) {
                    listeners.forEach { it.onNetworkAvailable(currentType) }
                    if (lastNetworkType != currentType) {
                        listeners.forEach { it.onNetworkTypeChanged(currentType) }
                    }
                } else {
                    listeners.forEach { it.onNetworkLost() }
                }
                
                lastNetworkType = currentType
            }
        }
    }
    
    fun addListener(listener: NetworkStateListener) {
        listeners.add(listener)
    }
    
    fun removeListener(listener: NetworkStateListener) {
        listeners.remove(listener)
    }
}

这个工具类提供了:

· ✅ 检测网络连接状态

· ✅ 区分 WiFi 和移动数据

· ✅ 实时网络状态监听

· ✅ 简洁的 API 调用

· ✅ 支持协程 StateFlow

· ✅ 兼容不同 Android 版本

可以直接在项目中使用,确保在网络请求前进行连接检查!

相关推荐
云宏信息3 小时前
【深度解析】VMware替代的关键一环:云宏ROW快照如何实现高频业务下的“无感”数据保护?
服务器·网络·数据库·架构·云计算·快照
我有一颗五叶草3 小时前
HTTP 协议
网络·网络协议·http
nvvas4 小时前
Android Studio JAVA开发按钮跳转功能
android·java·android studio
怪兽20144 小时前
Android多进程通信机制
android·面试
沐风ya4 小时前
RPC介绍
网络·网络协议·rpc
OAFD.4 小时前
YOLOv3 详解:核心改进、网络架构与目标检测实践
网络·yolo·目标检测
叶羽西4 小时前
Android CarService调试操作
android
千里马-horse5 小时前
在android中 spdlog库的log如何在控制台上输出
android·c++·spdlog
鹿鸣天涯5 小时前
商用密码应用安全性评估
网络·安全·web安全