Merge pull request #288 from chunfengyao/master-ObserveNetworkChanges

feat: observe network changes
This commit is contained in:
Jannis Mattheis
2023-05-02 18:53:12 +02:00
committed by GitHub
2 changed files with 37 additions and 19 deletions

View File

@@ -116,13 +116,18 @@ internal class WebSocketConnection(
@Synchronized @Synchronized
fun close() { fun close() {
if (webSocket != null) { if (webSocket != null) {
webSocket?.close(1000, "")
closed()
Log.i("WebSocket(${ID.get()}): closing existing connection.") Log.i("WebSocket(${ID.get()}): closing existing connection.")
state = State.Disconnected
webSocket!!.close(1000, "")
webSocket = null
} }
} }
@Synchronized
private fun closed() {
webSocket = null
state = State.Disconnected
}
@Synchronized @Synchronized
fun scheduleReconnect(seconds: Long) { fun scheduleReconnect(seconds: Long) {
if (state == State.Connecting || state == State.Connected) { if (state == State.Connecting || state == State.Connected) {
@@ -150,7 +155,7 @@ internal class WebSocketConnection(
private inner class Listener(private val id: Long) : WebSocketListener() { private inner class Listener(private val id: Long) : WebSocketListener() {
override fun onOpen(webSocket: WebSocket, response: Response) { override fun onOpen(webSocket: WebSocket, response: Response) {
syncExec { syncExec(id) {
state = State.Connected state = State.Connected
Log.i("WebSocket($id): opened") Log.i("WebSocket($id): opened")
onOpen.run() onOpen.run()
@@ -164,7 +169,7 @@ internal class WebSocketConnection(
} }
override fun onMessage(webSocket: WebSocket, text: String) { override fun onMessage(webSocket: WebSocket, text: String) {
syncExec { syncExec(id) {
Log.i("WebSocket($id): received message $text") Log.i("WebSocket($id): received message $text")
val message = Utils.JSON.fromJson(text, Message::class.java) val message = Utils.JSON.fromJson(text, Message::class.java)
onMessageCallback(message) onMessageCallback(message)
@@ -173,12 +178,12 @@ internal class WebSocketConnection(
} }
override fun onClosed(webSocket: WebSocket, code: Int, reason: String) { override fun onClosed(webSocket: WebSocket, code: Int, reason: String) {
syncExec { syncExec(id) {
if (state == State.Connected) { if (state == State.Connected) {
Log.w("WebSocket($id): closed") Log.w("WebSocket($id): closed")
onClose.run() onClose.run()
} }
state = State.Disconnected closed()
} }
super.onClosed(webSocket, code, reason) super.onClosed(webSocket, code, reason)
} }
@@ -187,11 +192,10 @@ internal class WebSocketConnection(
val code = if (response != null) "StatusCode: ${response.code()}" else "" val code = if (response != null) "StatusCode: ${response.code()}" else ""
val message = if (response != null) response.message() else "" val message = if (response != null) response.message() else ""
Log.e("WebSocket($id): failure $code Message: $message", t) Log.e("WebSocket($id): failure $code Message: $message", t)
syncExec { syncExec(id) {
state = State.Disconnected closed()
if (response != null && response.code() >= 400 && response.code() <= 499) { if (response != null && response.code() >= 400 && response.code() <= 499) {
onBadRequest.execute(message) onBadRequest.execute(message)
close()
return@syncExec return@syncExec
} }
@@ -209,13 +213,12 @@ internal class WebSocketConnection(
} }
super.onFailure(webSocket, t, response) super.onFailure(webSocket, t, response)
} }
}
private fun syncExec(runnable: Runnable) { @Synchronized
synchronized(this) { private fun syncExec(id: Long, runnable: () -> Unit) {
if (ID.get() == id) { if (ID.get() == id) {
runnable.run() runnable()
}
}
} }
} }

View File

@@ -5,9 +5,11 @@ import android.app.Notification
import android.app.NotificationManager import android.app.NotificationManager
import android.app.PendingIntent import android.app.PendingIntent
import android.app.Service import android.app.Service
import android.content.Context
import android.content.Intent import android.content.Intent
import android.graphics.Color import android.graphics.Color
import android.net.ConnectivityManager import android.net.ConnectivityManager
import android.net.Network
import android.net.Uri import android.net.Uri
import android.os.Build import android.os.Build
import android.os.IBinder import android.os.IBinder
@@ -43,6 +45,14 @@ internal class WebSocketService : Service() {
private lateinit var settings: Settings private lateinit var settings: Settings
private var connection: WebSocketConnection? = null private var connection: WebSocketConnection? = null
private val networkCallback: ConnectivityManager.NetworkCallback =
object : ConnectivityManager.NetworkCallback() {
override fun onAvailable(network: Network) {
super.onAvailable(network)
Log.i("WebSocket: Network available, reconnect if needed.")
connection?.start()
}
}
private val appIdToApp = ConcurrentHashMap<Long, Application>() private val appIdToApp = ConcurrentHashMap<Long, Application>()
private val lastReceivedMessage = AtomicLong(NOT_LOADED) private val lastReceivedMessage = AtomicLong(NOT_LOADED)
@@ -67,9 +77,12 @@ internal class WebSocketService : Service() {
override fun onDestroy() { override fun onDestroy() {
super.onDestroy() super.onDestroy()
if (connection != null) { connection?.close()
connection!!.close() if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
(getSystemService(Context.CONNECTIVITY_SERVICE) as ConnectivityManager)
.unregisterNetworkCallback(networkCallback)
} }
Log.w("Destroy ${javaClass.simpleName}") Log.w("Destroy ${javaClass.simpleName}")
} }
@@ -110,7 +123,9 @@ internal class WebSocketService : Service() {
.onMessage { message -> onMessage(message) } .onMessage { message -> onMessage(message) }
.onReconnected { notifyMissedNotifications() } .onReconnected { notifyMissedNotifications() }
.start() .start()
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
cm.registerDefaultNetworkCallback(networkCallback)
}
fetchApps() fetchApps()
} }