fix: resolve auto-connect race conditions and pairing success redirects
This commit is contained in:
@@ -125,8 +125,8 @@ fun Application.module() {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Send pairing success indicator screen only if we actually paired in this session
|
// Send pairing success indicator screen only if we actually paired in this session AND no specific profile was requested
|
||||||
if (showedPairingScreen) {
|
if (showedPairingScreen && profileId == null) {
|
||||||
val successMessage = Message(
|
val successMessage = Message(
|
||||||
id = "pairing_success_$deviceId",
|
id = "pairing_success_$deviceId",
|
||||||
title = "Pairing Successful",
|
title = "Pairing Successful",
|
||||||
|
|||||||
@@ -95,6 +95,11 @@ class MainActivity : ComponentActivity() {
|
|||||||
|
|
||||||
// SharedPreferences for connection details
|
// SharedPreferences for connection details
|
||||||
val prefs = getSharedPreferences("meatbag_prefs", Context.MODE_PRIVATE)
|
val prefs = getSharedPreferences("meatbag_prefs", Context.MODE_PRIVATE)
|
||||||
|
val deviceId = prefs.getString("device_id", null) ?: run {
|
||||||
|
val newId = java.util.UUID.randomUUID().toString()
|
||||||
|
prefs.edit().putString("device_id", newId).apply()
|
||||||
|
newId
|
||||||
|
}
|
||||||
|
|
||||||
setContent {
|
setContent {
|
||||||
var host by remember { mutableStateOf(prefs.getString("host", "10.0.0.7") ?: "10.0.0.7") }
|
var host by remember { mutableStateOf(prefs.getString("host", "10.0.0.7") ?: "10.0.0.7") }
|
||||||
@@ -110,18 +115,21 @@ class MainActivity : ComponentActivity() {
|
|||||||
var errorMessage by remember { mutableStateOf<String?>(null) }
|
var errorMessage by remember { mutableStateOf<String?>(null) }
|
||||||
|
|
||||||
var activeProfileId by remember { mutableStateOf(intent.getStringExtra("LAUNCH_PROFILE_ID")) }
|
var activeProfileId by remember { mutableStateOf(intent.getStringExtra("LAUNCH_PROFILE_ID")) }
|
||||||
|
var isInitialLaunch by remember { mutableStateOf(true) }
|
||||||
LaunchedEffect(Unit) {
|
LaunchedEffect(Unit) {
|
||||||
onProfileLaunch = { id ->
|
onProfileLaunch = { id ->
|
||||||
activeProfileId = id
|
activeProfileId = id
|
||||||
|
isInitialLaunch = true
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Auto-connect when a specific profile is launched via shortcut or intent
|
// Auto-connect when a specific profile is launched via shortcut or intent on startup/new intent
|
||||||
LaunchedEffect(activeProfileId) {
|
LaunchedEffect(activeProfileId) {
|
||||||
if (activeProfileId != null && connectionState == ConnectionState.DISCONNECTED && clientState == null) {
|
if (isInitialLaunch && activeProfileId != null && connectionState == ConnectionState.DISCONNECTED && clientState == null) {
|
||||||
|
isInitialLaunch = false
|
||||||
errorMessage = null
|
errorMessage = null
|
||||||
scope.launch(Dispatchers.Default) {
|
scope.launch(Dispatchers.Default) {
|
||||||
val newClient = MeatbagClient(host.trim(), portStr.trim().toIntOrNull() ?: 8080, feedback)
|
val newClient = MeatbagClient(host.trim(), portStr.trim().toIntOrNull() ?: 8080, feedback, deviceId = deviceId)
|
||||||
clientState = newClient
|
clientState = newClient
|
||||||
newClient.connect(deviceType, activeProfileId)
|
newClient.connect(deviceType, activeProfileId)
|
||||||
}
|
}
|
||||||
@@ -380,6 +388,7 @@ class MainActivity : ComponentActivity() {
|
|||||||
|
|
||||||
Button(
|
Button(
|
||||||
onClick = {
|
onClick = {
|
||||||
|
isInitialLaunch = false
|
||||||
errorMessage = null
|
errorMessage = null
|
||||||
// Save preferences
|
// Save preferences
|
||||||
prefs.edit().apply {
|
prefs.edit().apply {
|
||||||
@@ -405,7 +414,8 @@ class MainActivity : ComponentActivity() {
|
|||||||
host = host.trim(),
|
host = host.trim(),
|
||||||
port = portStr.trim().toIntOrNull() ?: 8080,
|
port = portStr.trim().toIntOrNull() ?: 8080,
|
||||||
attentionFeedback = feedback,
|
attentionFeedback = feedback,
|
||||||
socksPort = socksPort
|
socksPort = socksPort,
|
||||||
|
deviceId = deviceId
|
||||||
)
|
)
|
||||||
clientState = newClient
|
clientState = newClient
|
||||||
newClient.connect(deviceType, activeProfileId)
|
newClient.connect(deviceType, activeProfileId)
|
||||||
@@ -471,9 +481,10 @@ class MainActivity : ComponentActivity() {
|
|||||||
Button(
|
Button(
|
||||||
onClick = {
|
onClick = {
|
||||||
activeProfileId = "meatbag"
|
activeProfileId = "meatbag"
|
||||||
|
isInitialLaunch = false
|
||||||
errorMessage = null
|
errorMessage = null
|
||||||
scope.launch(Dispatchers.Default) {
|
scope.launch(Dispatchers.Default) {
|
||||||
val newClient = MeatbagClient(host.trim(), portStr.trim().toIntOrNull() ?: 8080, feedback)
|
val newClient = MeatbagClient(host.trim(), portStr.trim().toIntOrNull() ?: 8080, feedback, deviceId = deviceId)
|
||||||
clientState = newClient
|
clientState = newClient
|
||||||
newClient.connect(deviceType, "meatbag")
|
newClient.connect(deviceType, "meatbag")
|
||||||
}
|
}
|
||||||
@@ -513,9 +524,10 @@ class MainActivity : ComponentActivity() {
|
|||||||
Button(
|
Button(
|
||||||
onClick = {
|
onClick = {
|
||||||
activeProfileId = "lm_studio_remote"
|
activeProfileId = "lm_studio_remote"
|
||||||
|
isInitialLaunch = false
|
||||||
errorMessage = null
|
errorMessage = null
|
||||||
scope.launch(Dispatchers.Default) {
|
scope.launch(Dispatchers.Default) {
|
||||||
val newClient = MeatbagClient(host.trim(), portStr.trim().toIntOrNull() ?: 8080, feedback)
|
val newClient = MeatbagClient(host.trim(), portStr.trim().toIntOrNull() ?: 8080, feedback, deviceId = deviceId)
|
||||||
clientState = newClient
|
clientState = newClient
|
||||||
newClient.connect(deviceType, "lm_studio_remote")
|
newClient.connect(deviceType, "lm_studio_remote")
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -35,7 +35,8 @@ class MeatbagClient(
|
|||||||
private val host: String = "localhost",
|
private val host: String = "localhost",
|
||||||
private val port: Int = 8080,
|
private val port: Int = 8080,
|
||||||
private val attentionFeedback: AttentionFeedback = NoOpAttentionFeedback,
|
private val attentionFeedback: AttentionFeedback = NoOpAttentionFeedback,
|
||||||
private val socksPort: Int? = null
|
private val socksPort: Int? = null,
|
||||||
|
private val deviceId: String? = null
|
||||||
) {
|
) {
|
||||||
private val jsonConfig = Json {
|
private val jsonConfig = Json {
|
||||||
ignoreUnknownKeys = true
|
ignoreUnknownKeys = true
|
||||||
@@ -76,10 +77,17 @@ class MeatbagClient(
|
|||||||
connectionJob = CoroutineScope(Dispatchers.Default).launch {
|
connectionJob = CoroutineScope(Dispatchers.Default).launch {
|
||||||
while (isActive) {
|
while (isActive) {
|
||||||
try {
|
try {
|
||||||
val queryParams = if (profileId != null) {
|
val queryParams = buildString {
|
||||||
"?deviceType=$deviceType&profileId=$profileId"
|
append("?deviceType=")
|
||||||
} else {
|
append(deviceType)
|
||||||
"?deviceType=$deviceType"
|
if (profileId != null) {
|
||||||
|
append("&profileId=")
|
||||||
|
append(profileId)
|
||||||
|
}
|
||||||
|
if (deviceId != null) {
|
||||||
|
append("&deviceId=")
|
||||||
|
append(deviceId)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
log("Connecting to ws://$host:$port/ws/connect$queryParams ...")
|
log("Connecting to ws://$host:$port/ws/connect$queryParams ...")
|
||||||
_connectionState.value = ConnectionState.CONNECTING
|
_connectionState.value = ConnectionState.CONNECTING
|
||||||
|
|||||||
Reference in New Issue
Block a user