feat: add setting to keep connection alive in background (#1196)

This commit is contained in:
M57 authored and GitHub committed 2026-09-19 18:28:48 +03:00
1 parent a61a1b9974
commit 759d59b9f9
19 files changed
+1155 -24

No files matched your search

@@ -114,7 +114,9 @@ fun SettingsScreen(
icon = Icons.Filled.Tune,
label = stringResource(R.string.settings_sec_behavior),
summary =
if (state.autoReconnect || state.restoreLastSession) {
if (state.autoReconnect || state.restoreLastSession ||
state.keepConnectedInBackground
) {
stringResource(R.string.settings_summary_on)
} else {
stringResource(R.string.settings_summary_off)
@@ -237,6 +237,8 @@ internal fun SettingsBehaviorPage(
BehaviorSection(
autoReconnect = state.autoReconnect,
onAutoReconnectChange = viewModel::onAutoReconnectChange,
keepConnectedInBackground = state.keepConnectedInBackground,
onKeepConnectedInBackgroundChange = viewModel::onKeepConnectedInBackgroundChange,
restoreLastSession = state.restoreLastSession,
onRestoreLastSessionChange = viewModel::onRestoreLastSessionChange,
)
@@ -44,6 +44,7 @@ data class SettingsUiState(
val showAssistantMessageTokens: Boolean = true,
val showTokensPerSecond: Boolean = true,
val showModelProvider: Boolean = false,
val keepConnectedInBackground: Boolean = false,
val profiles: List<ConnectionProfile> = emptyList(),
val selectedProfileId: String? = null,
val renameProfileName: String = "",
@@ -91,6 +92,7 @@ class SettingsViewModel(
val showAssistantMessageTokens = AuthManager.isAssistantMessageTokensEnabled()
val showTokensPerSecond = AuthManager.isTokensPerSecondEnabled()
val showModelProvider = AuthManager.isModelProviderShown()
val keepConnectedInBackground = AuthManager.isKeepConnectedInBackground()
val profiles = AuthManager.getConnectionProfiles()
val appLanguage = AuthManager.getAppLanguage()
val renameProfileName =
@@ -117,6 +119,7 @@ class SettingsViewModel(
showAssistantMessageTokens = showAssistantMessageTokens,
showTokensPerSecond = showTokensPerSecond,
showModelProvider = showModelProvider,
keepConnectedInBackground = keepConnectedInBackground,
profiles = profiles,
selectedProfileId = selectedId,
renameProfileName = renameProfileName,
@@ -368,6 +371,11 @@ class SettingsViewModel(
AuthManager.setModelProviderShown(enabled)
}
fun onKeepConnectedInBackgroundChange(enabled: Boolean) {
_uiState.update { it.copy(keepConnectedInBackground = enabled) }
AuthManager.setKeepConnectedInBackground(enabled)
}
/** Clear all auth credentials — logs out and returns to landing screen. */
fun logout() {
AuthManager.setToken(null)
@@ -402,6 +410,7 @@ class SettingsViewModel(
AuthManager.setAssistantMessageTokensEnabled(state.showAssistantMessageTokens)
AuthManager.setTokensPerSecondEnabled(state.showTokensPerSecond)
AuthManager.setModelProviderShown(state.showModelProvider)
AuthManager.setKeepConnectedInBackground(state.keepConnectedInBackground)
ApiClient.rebuild()
viewModelScope.launch(ioDispatcher) {
@@ -23,6 +23,8 @@ import com.m57.hermescontrol.ui.settings.SectionCard
internal fun BehaviorSection(
autoReconnect: Boolean,
onAutoReconnectChange: (Boolean) -> Unit,
keepConnectedInBackground: Boolean,
onKeepConnectedInBackgroundChange: (Boolean) -> Unit,
restoreLastSession: Boolean,
onRestoreLastSessionChange: (Boolean) -> Unit,
) {
@@ -60,6 +62,39 @@ internal fun BehaviorSection(
HorizontalDivider(color = MaterialTheme.colorScheme.outlineVariant)
Spacer(modifier = Modifier.height(12.dp))
Row(
modifier = Modifier.fillMaxWidth(),
horizontalArrangement = Arrangement.SpaceBetween,
verticalAlignment = Alignment.CenterVertically,
) {
Column(modifier = Modifier.weight(1f)) {
Text(
text = stringResource(R.string.settings_keep_connected_in_background_title),
style = MaterialTheme.typography.bodyLarge,
)
Text(
text = stringResource(R.string.settings_keep_connected_in_background_desc),
style =
MaterialTheme.typography.bodySmall.copy(
color = MaterialTheme.colorScheme.onSurfaceVariant,
),
)
}
Switch(
checked = keepConnectedInBackground,
onCheckedChange = onKeepConnectedInBackgroundChange,
colors =
SwitchDefaults.colors(
checkedThumbColor = MaterialTheme.colorScheme.primary,
checkedTrackColor = MaterialTheme.colorScheme.primaryContainer,
),
)
}
Spacer(modifier = Modifier.height(12.dp))
HorizontalDivider(color = MaterialTheme.colorScheme.outlineVariant)
Spacer(modifier = Modifier.height(12.dp))
Row(
modifier = Modifier.fillMaxWidth(),
horizontalArrangement = Arrangement.SpaceBetween,