Loading packages/SystemUI/multivalentTests/src/com/android/systemui/statusbar/pipeline/airplane/data/repository/AirplaneModeRepositoryImplTest.kt→packages/SystemUI/multivalentTests/src/com/android/systemui/statusbar/pipeline/airplane/data/repository/impl/AirplaneModeRepositoryImplTest.kt +3 −2 Original line number Diff line number Diff line /* * Copyright (C) 2022 The Android Open Source Project * Copyright (C) 2025 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. Loading @@ -14,7 +14,7 @@ * limitations under the License. */ package com.android.systemui.statusbar.pipeline.airplane.data.repository package com.android.systemui.statusbar.pipeline.airplane.data.repository.impl import android.net.ConnectivityManager import android.provider.Settings.Global Loading @@ -24,6 +24,7 @@ import androidx.test.ext.junit.runners.AndroidJUnit4 import androidx.test.filters.SmallTest import com.android.systemui.SysuiTestCase import com.android.systemui.log.table.TableLogBuffer import com.android.systemui.statusbar.pipeline.airplane.data.repository.AirplaneModeRepository import com.android.systemui.util.mockito.eq import com.android.systemui.util.mockito.whenever import com.android.systemui.util.settings.FakeGlobalSettings Loading packages/SystemUI/src/com/android/systemui/statusbar/pipeline/airplane/data/repository/AirplaneModeDataLayerModule.kt 0 → 100644 +40 −0 Original line number Diff line number Diff line /* * Copyright (C) 2025 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package com.android.systemui.statusbar.pipeline.airplane.data.repository import com.android.systemui.dagger.SysUISingleton import com.android.systemui.log.table.TableLogBuffer import com.android.systemui.log.table.TableLogBufferFactory import com.android.systemui.statusbar.pipeline.airplane.data.repository.impl.AirplaneModeRepositoryImpl import com.android.systemui.statusbar.pipeline.airplane.shared.AirplaneTableLog import dagger.Binds import dagger.Module import dagger.Provides @Module interface AirplaneModeDataLayerModule { @Binds fun airplaneModeRepository(impl: AirplaneModeRepositoryImpl): AirplaneModeRepository companion object { @Provides @SysUISingleton @AirplaneTableLog fun provideAirplaneTableLogBuffer(factory: TableLogBufferFactory): TableLogBuffer { return factory.create("AirplaneTableLog", 30) } } } packages/SystemUI/src/com/android/systemui/statusbar/pipeline/airplane/data/repository/AirplaneModeRepository.kt +1 −60 Original line number Diff line number Diff line /* * Copyright (C) 2022 The Android Open Source Project * Copyright (C) 2025 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. Loading @@ -16,26 +16,7 @@ package com.android.systemui.statusbar.pipeline.airplane.data.repository import android.net.ConnectivityManager import android.os.Handler import android.provider.Settings.Global import com.android.systemui.dagger.SysUISingleton import com.android.systemui.dagger.qualifiers.Background import com.android.systemui.log.table.TableLogBuffer import com.android.systemui.log.table.logDiffsForTable import com.android.systemui.statusbar.pipeline.dagger.AirplaneTableLog import com.android.systemui.util.settings.GlobalSettings import com.android.systemui.util.settings.SettingObserver import com.android.systemui.utils.coroutines.flow.conflatedCallbackFlow import javax.inject.Inject import kotlin.coroutines.CoroutineContext import kotlinx.coroutines.CoroutineScope import kotlinx.coroutines.channels.awaitClose import kotlinx.coroutines.flow.SharingStarted import kotlinx.coroutines.flow.StateFlow import kotlinx.coroutines.flow.distinctUntilChanged import kotlinx.coroutines.flow.stateIn import kotlinx.coroutines.withContext /** Provides data related to airplane mode. */ interface AirplaneModeRepository { Loading @@ -45,43 +26,3 @@ interface AirplaneModeRepository { /** Sets airplane mode state. */ suspend fun setIsAirplaneMode(isEnabled: Boolean) } @SysUISingleton @Suppress("EXPERIMENTAL_IS_NOT_ENABLED") class AirplaneModeRepositoryImpl @Inject constructor( private val connectivityManager: ConnectivityManager, @Background private val bgHandler: Handler?, @Background private val backgroundContext: CoroutineContext, private val globalSettings: GlobalSettings, @AirplaneTableLog logger: TableLogBuffer, @Background scope: CoroutineScope, ) : AirplaneModeRepository { // TODO(b/254848912): Replace this with a generic SettingObserver coroutine once we have it. override val isAirplaneMode: StateFlow<Boolean> = conflatedCallbackFlow { val observer = object : SettingObserver(globalSettings, bgHandler, Global.AIRPLANE_MODE_ON) { override fun handleValueChanged(value: Int, observedChange: Boolean) { trySend(value == 1) } } observer.isListening = true trySend(observer.value == 1) awaitClose { observer.isListening = false } } .distinctUntilChanged() .logDiffsForTable(logger, columnName = "isAirplaneMode", initialValue = false) .stateIn( scope, started = SharingStarted.WhileSubscribed(), // When the observer starts listening, the flow will emit the current value so the // initialValue here is irrelevant. initialValue = false, ) override suspend fun setIsAirplaneMode(isEnabled: Boolean) = withContext(backgroundContext) { connectivityManager.setAirplaneMode(isEnabled) } } packages/SystemUI/src/com/android/systemui/statusbar/pipeline/airplane/data/repository/impl/AirplaneModeRepositoryImpl.kt 0 → 100644 +79 −0 Original line number Diff line number Diff line /* * Copyright (C) 2022 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package com.android.systemui.statusbar.pipeline.airplane.data.repository.impl import android.net.ConnectivityManager import android.os.Handler import android.provider.Settings.Global import com.android.systemui.dagger.SysUISingleton import com.android.systemui.dagger.qualifiers.Background import com.android.systemui.log.table.TableLogBuffer import com.android.systemui.log.table.logDiffsForTable import com.android.systemui.statusbar.pipeline.airplane.data.repository.AirplaneModeRepository import com.android.systemui.statusbar.pipeline.airplane.shared.AirplaneTableLog import com.android.systemui.util.settings.GlobalSettings import com.android.systemui.util.settings.SettingObserver import com.android.systemui.utils.coroutines.flow.conflatedCallbackFlow import javax.inject.Inject import kotlin.coroutines.CoroutineContext import kotlinx.coroutines.CoroutineScope import kotlinx.coroutines.channels.awaitClose import kotlinx.coroutines.flow.SharingStarted import kotlinx.coroutines.flow.StateFlow import kotlinx.coroutines.flow.distinctUntilChanged import kotlinx.coroutines.flow.stateIn import kotlinx.coroutines.withContext @SysUISingleton @Suppress("EXPERIMENTAL_IS_NOT_ENABLED") class AirplaneModeRepositoryImpl @Inject constructor( private val connectivityManager: ConnectivityManager, @Background private val bgHandler: Handler?, @Background private val backgroundContext: CoroutineContext, private val globalSettings: GlobalSettings, @AirplaneTableLog logger: TableLogBuffer, @Background scope: CoroutineScope, ) : AirplaneModeRepository { // TODO(b/254848912): Replace this with a generic SettingObserver coroutine once we have it. override val isAirplaneMode: StateFlow<Boolean> = conflatedCallbackFlow { val observer = object : SettingObserver(globalSettings, bgHandler, Global.AIRPLANE_MODE_ON) { override fun handleValueChanged(value: Int, observedChange: Boolean) { trySend(value == 1) } } observer.isListening = true trySend(observer.value == 1) awaitClose { observer.isListening = false } } .distinctUntilChanged() .logDiffsForTable(logger, columnName = "isAirplaneMode", initialValue = false) .stateIn( scope, started = SharingStarted.WhileSubscribed(), // When the observer starts listening, the flow will emit the current value so the // initialValue here is irrelevant. initialValue = false, ) override suspend fun setIsAirplaneMode(isEnabled: Boolean) = withContext(backgroundContext) { connectivityManager.setAirplaneMode(isEnabled) } } packages/SystemUI/src/com/android/systemui/statusbar/pipeline/dagger/AirplaneTableLog.kt→packages/SystemUI/src/com/android/systemui/statusbar/pipeline/airplane/shared/AirplaneTableLog.kt +2 −2 Original line number Diff line number Diff line Loading @@ -14,12 +14,12 @@ * limitations under the License. */ package com.android.systemui.statusbar.pipeline.dagger package com.android.systemui.statusbar.pipeline.airplane.shared import javax.inject.Qualifier /** Airplane mode logs in table format. */ @Qualifier @MustBeDocumented @kotlin.annotation.Retention(AnnotationRetention.RUNTIME) @Retention(AnnotationRetention.RUNTIME) annotation class AirplaneTableLog Loading
packages/SystemUI/multivalentTests/src/com/android/systemui/statusbar/pipeline/airplane/data/repository/AirplaneModeRepositoryImplTest.kt→packages/SystemUI/multivalentTests/src/com/android/systemui/statusbar/pipeline/airplane/data/repository/impl/AirplaneModeRepositoryImplTest.kt +3 −2 Original line number Diff line number Diff line /* * Copyright (C) 2022 The Android Open Source Project * Copyright (C) 2025 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. Loading @@ -14,7 +14,7 @@ * limitations under the License. */ package com.android.systemui.statusbar.pipeline.airplane.data.repository package com.android.systemui.statusbar.pipeline.airplane.data.repository.impl import android.net.ConnectivityManager import android.provider.Settings.Global Loading @@ -24,6 +24,7 @@ import androidx.test.ext.junit.runners.AndroidJUnit4 import androidx.test.filters.SmallTest import com.android.systemui.SysuiTestCase import com.android.systemui.log.table.TableLogBuffer import com.android.systemui.statusbar.pipeline.airplane.data.repository.AirplaneModeRepository import com.android.systemui.util.mockito.eq import com.android.systemui.util.mockito.whenever import com.android.systemui.util.settings.FakeGlobalSettings Loading
packages/SystemUI/src/com/android/systemui/statusbar/pipeline/airplane/data/repository/AirplaneModeDataLayerModule.kt 0 → 100644 +40 −0 Original line number Diff line number Diff line /* * Copyright (C) 2025 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package com.android.systemui.statusbar.pipeline.airplane.data.repository import com.android.systemui.dagger.SysUISingleton import com.android.systemui.log.table.TableLogBuffer import com.android.systemui.log.table.TableLogBufferFactory import com.android.systemui.statusbar.pipeline.airplane.data.repository.impl.AirplaneModeRepositoryImpl import com.android.systemui.statusbar.pipeline.airplane.shared.AirplaneTableLog import dagger.Binds import dagger.Module import dagger.Provides @Module interface AirplaneModeDataLayerModule { @Binds fun airplaneModeRepository(impl: AirplaneModeRepositoryImpl): AirplaneModeRepository companion object { @Provides @SysUISingleton @AirplaneTableLog fun provideAirplaneTableLogBuffer(factory: TableLogBufferFactory): TableLogBuffer { return factory.create("AirplaneTableLog", 30) } } }
packages/SystemUI/src/com/android/systemui/statusbar/pipeline/airplane/data/repository/AirplaneModeRepository.kt +1 −60 Original line number Diff line number Diff line /* * Copyright (C) 2022 The Android Open Source Project * Copyright (C) 2025 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. Loading @@ -16,26 +16,7 @@ package com.android.systemui.statusbar.pipeline.airplane.data.repository import android.net.ConnectivityManager import android.os.Handler import android.provider.Settings.Global import com.android.systemui.dagger.SysUISingleton import com.android.systemui.dagger.qualifiers.Background import com.android.systemui.log.table.TableLogBuffer import com.android.systemui.log.table.logDiffsForTable import com.android.systemui.statusbar.pipeline.dagger.AirplaneTableLog import com.android.systemui.util.settings.GlobalSettings import com.android.systemui.util.settings.SettingObserver import com.android.systemui.utils.coroutines.flow.conflatedCallbackFlow import javax.inject.Inject import kotlin.coroutines.CoroutineContext import kotlinx.coroutines.CoroutineScope import kotlinx.coroutines.channels.awaitClose import kotlinx.coroutines.flow.SharingStarted import kotlinx.coroutines.flow.StateFlow import kotlinx.coroutines.flow.distinctUntilChanged import kotlinx.coroutines.flow.stateIn import kotlinx.coroutines.withContext /** Provides data related to airplane mode. */ interface AirplaneModeRepository { Loading @@ -45,43 +26,3 @@ interface AirplaneModeRepository { /** Sets airplane mode state. */ suspend fun setIsAirplaneMode(isEnabled: Boolean) } @SysUISingleton @Suppress("EXPERIMENTAL_IS_NOT_ENABLED") class AirplaneModeRepositoryImpl @Inject constructor( private val connectivityManager: ConnectivityManager, @Background private val bgHandler: Handler?, @Background private val backgroundContext: CoroutineContext, private val globalSettings: GlobalSettings, @AirplaneTableLog logger: TableLogBuffer, @Background scope: CoroutineScope, ) : AirplaneModeRepository { // TODO(b/254848912): Replace this with a generic SettingObserver coroutine once we have it. override val isAirplaneMode: StateFlow<Boolean> = conflatedCallbackFlow { val observer = object : SettingObserver(globalSettings, bgHandler, Global.AIRPLANE_MODE_ON) { override fun handleValueChanged(value: Int, observedChange: Boolean) { trySend(value == 1) } } observer.isListening = true trySend(observer.value == 1) awaitClose { observer.isListening = false } } .distinctUntilChanged() .logDiffsForTable(logger, columnName = "isAirplaneMode", initialValue = false) .stateIn( scope, started = SharingStarted.WhileSubscribed(), // When the observer starts listening, the flow will emit the current value so the // initialValue here is irrelevant. initialValue = false, ) override suspend fun setIsAirplaneMode(isEnabled: Boolean) = withContext(backgroundContext) { connectivityManager.setAirplaneMode(isEnabled) } }
packages/SystemUI/src/com/android/systemui/statusbar/pipeline/airplane/data/repository/impl/AirplaneModeRepositoryImpl.kt 0 → 100644 +79 −0 Original line number Diff line number Diff line /* * Copyright (C) 2022 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package com.android.systemui.statusbar.pipeline.airplane.data.repository.impl import android.net.ConnectivityManager import android.os.Handler import android.provider.Settings.Global import com.android.systemui.dagger.SysUISingleton import com.android.systemui.dagger.qualifiers.Background import com.android.systemui.log.table.TableLogBuffer import com.android.systemui.log.table.logDiffsForTable import com.android.systemui.statusbar.pipeline.airplane.data.repository.AirplaneModeRepository import com.android.systemui.statusbar.pipeline.airplane.shared.AirplaneTableLog import com.android.systemui.util.settings.GlobalSettings import com.android.systemui.util.settings.SettingObserver import com.android.systemui.utils.coroutines.flow.conflatedCallbackFlow import javax.inject.Inject import kotlin.coroutines.CoroutineContext import kotlinx.coroutines.CoroutineScope import kotlinx.coroutines.channels.awaitClose import kotlinx.coroutines.flow.SharingStarted import kotlinx.coroutines.flow.StateFlow import kotlinx.coroutines.flow.distinctUntilChanged import kotlinx.coroutines.flow.stateIn import kotlinx.coroutines.withContext @SysUISingleton @Suppress("EXPERIMENTAL_IS_NOT_ENABLED") class AirplaneModeRepositoryImpl @Inject constructor( private val connectivityManager: ConnectivityManager, @Background private val bgHandler: Handler?, @Background private val backgroundContext: CoroutineContext, private val globalSettings: GlobalSettings, @AirplaneTableLog logger: TableLogBuffer, @Background scope: CoroutineScope, ) : AirplaneModeRepository { // TODO(b/254848912): Replace this with a generic SettingObserver coroutine once we have it. override val isAirplaneMode: StateFlow<Boolean> = conflatedCallbackFlow { val observer = object : SettingObserver(globalSettings, bgHandler, Global.AIRPLANE_MODE_ON) { override fun handleValueChanged(value: Int, observedChange: Boolean) { trySend(value == 1) } } observer.isListening = true trySend(observer.value == 1) awaitClose { observer.isListening = false } } .distinctUntilChanged() .logDiffsForTable(logger, columnName = "isAirplaneMode", initialValue = false) .stateIn( scope, started = SharingStarted.WhileSubscribed(), // When the observer starts listening, the flow will emit the current value so the // initialValue here is irrelevant. initialValue = false, ) override suspend fun setIsAirplaneMode(isEnabled: Boolean) = withContext(backgroundContext) { connectivityManager.setAirplaneMode(isEnabled) } }
packages/SystemUI/src/com/android/systemui/statusbar/pipeline/dagger/AirplaneTableLog.kt→packages/SystemUI/src/com/android/systemui/statusbar/pipeline/airplane/shared/AirplaneTableLog.kt +2 −2 Original line number Diff line number Diff line Loading @@ -14,12 +14,12 @@ * limitations under the License. */ package com.android.systemui.statusbar.pipeline.dagger package com.android.systemui.statusbar.pipeline.airplane.shared import javax.inject.Qualifier /** Airplane mode logs in table format. */ @Qualifier @MustBeDocumented @kotlin.annotation.Retention(AnnotationRetention.RUNTIME) @Retention(AnnotationRetention.RUNTIME) annotation class AirplaneTableLog