diff --git a/app/src/androidTest/java/com/duckduckgo/app/browser/WebViewDataManagerTest.kt b/app/src/androidTest/java/com/duckduckgo/app/browser/WebViewDataManagerTest.kt index 898dead27cc2..f3bd4bf4caac 100644 --- a/app/src/androidTest/java/com/duckduckgo/app/browser/WebViewDataManagerTest.kt +++ b/app/src/androidTest/java/com/duckduckgo/app/browser/WebViewDataManagerTest.kt @@ -26,7 +26,9 @@ import androidx.test.platform.app.InstrumentationRegistry import com.duckduckgo.app.browser.httpauth.WebViewHttpAuthStore import com.duckduckgo.app.browser.session.WebViewSessionInMemoryStorage import com.duckduckgo.app.global.file.FileDeleter +import com.duckduckgo.app.pixels.remoteconfig.AndroidBrowserConfigFeature import com.duckduckgo.cookies.api.DuckDuckGoCookieManager +import com.duckduckgo.feature.toggles.api.FakeFeatureToggleFactory import kotlinx.coroutines.Dispatchers import kotlinx.coroutines.test.runTest import kotlinx.coroutines.withContext @@ -49,7 +51,15 @@ class WebViewDataManagerTest { private val context = InstrumentationRegistry.getInstrumentation().targetContext private val mockFileDeleter: FileDeleter = mock() private val mockWebViewHttpAuthStore: WebViewHttpAuthStore = mock() - private val testee = WebViewDataManager(context, WebViewSessionInMemoryStorage(), mockCookieManager, mockFileDeleter, mockWebViewHttpAuthStore) + private val feature = FakeFeatureToggleFactory.create(AndroidBrowserConfigFeature::class.java) + private val testee = WebViewDataManager( + context, + WebViewSessionInMemoryStorage(), + mockCookieManager, + mockFileDeleter, + mockWebViewHttpAuthStore, + feature, + ) @Before fun setup() { diff --git a/app/src/main/java/com/duckduckgo/app/browser/WebDataManager.kt b/app/src/main/java/com/duckduckgo/app/browser/WebDataManager.kt index 0602e53b3a06..da52c34e27d0 100644 --- a/app/src/main/java/com/duckduckgo/app/browser/WebDataManager.kt +++ b/app/src/main/java/com/duckduckgo/app/browser/WebDataManager.kt @@ -23,11 +23,16 @@ import android.webkit.WebView import com.duckduckgo.app.browser.httpauth.WebViewHttpAuthStore import com.duckduckgo.app.browser.session.WebViewSessionStorage import com.duckduckgo.app.global.file.FileDeleter +import com.duckduckgo.app.pixels.remoteconfig.AndroidBrowserConfigFeature import com.duckduckgo.cookies.api.DuckDuckGoCookieManager +import com.duckduckgo.di.scopes.AppScope +import com.squareup.anvil.annotations.ContributesBinding +import dagger.SingleInstanceIn import java.io.File import javax.inject.Inject import kotlin.coroutines.resume import kotlin.coroutines.suspendCoroutine +import timber.log.Timber interface WebDataManager { suspend fun clearData( @@ -38,12 +43,15 @@ interface WebDataManager { fun clearWebViewSessions() } +@ContributesBinding(AppScope::class) +@SingleInstanceIn(AppScope::class) class WebViewDataManager @Inject constructor( private val context: Context, private val webViewSessionStorage: WebViewSessionStorage, private val cookieManager: DuckDuckGoCookieManager, private val fileDeleter: FileDeleter, private val webViewHttpAuthStore: WebViewHttpAuthStore, + private val androidBrowserConfigFeature: AndroidBrowserConfigFeature, ) : WebDataManager { override suspend fun clearData( @@ -77,6 +85,7 @@ class WebViewDataManager @Inject constructor( // Check if this is the domain to exclude if (!originString.endsWith(".duckduckgo.com")) { // Delete all other origins + Timber.d("aitor delete $originString / $origin") webStorage.deleteOrigin(originString) } } @@ -107,7 +116,11 @@ class WebViewDataManager @Inject constructor( fileDeleter.deleteContents(File(dataDir, "app_webview"), listOf("Default", "Cookies")) // We don't delete the Default dir as Cookies may be inside however we do clear any other content - fileDeleter.deleteContents(File(dataDir, "app_webview/Default"), listOf("Cookies", "Local Storage")) + if (androidBrowserConfigFeature.deleteLocalStorageKillSwitch().isEnabled()) { + fileDeleter.deleteContents(File(dataDir, "app_webview/Default"), listOf("Cookies")) + } else { + fileDeleter.deleteContents(File(dataDir, "app_webview/Default"), listOf("Cookies", "Local Storage")) + } } private suspend fun clearAuthentication(webView: WebView) { diff --git a/app/src/main/java/com/duckduckgo/app/browser/di/BrowserModule.kt b/app/src/main/java/com/duckduckgo/app/browser/di/BrowserModule.kt index 2d78f0857f1b..98876d97a533 100644 --- a/app/src/main/java/com/duckduckgo/app/browser/di/BrowserModule.kt +++ b/app/src/main/java/com/duckduckgo/app/browser/di/BrowserModule.kt @@ -74,7 +74,6 @@ import com.duckduckgo.app.trackerdetection.CloakedCnameDetector import com.duckduckgo.app.trackerdetection.TrackerDetector import com.duckduckgo.common.utils.DispatcherProvider import com.duckduckgo.cookies.api.CookieManagerProvider -import com.duckduckgo.cookies.api.DuckDuckGoCookieManager import com.duckduckgo.cookies.api.ThirdPartyCookieNames import com.duckduckgo.customtabs.api.CustomTabDetector import com.duckduckgo.di.scopes.AppScope @@ -159,17 +158,6 @@ class BrowserModule { @Provides fun webViewSessionStorage(): WebViewSessionStorage = WebViewSessionInMemoryStorage() - @SingleInstanceIn(AppScope::class) - @Provides - fun webDataManager( - context: Context, - webViewSessionStorage: WebViewSessionStorage, - cookieManager: DuckDuckGoCookieManager, - fileDeleter: FileDeleter, - webViewHttpAuthStore: WebViewHttpAuthStore, - ): WebDataManager = - WebViewDataManager(context, webViewSessionStorage, cookieManager, fileDeleter, webViewHttpAuthStore) - @Provides fun clipboardManager(context: Context): ClipboardManager { return context.getSystemService(Context.CLIPBOARD_SERVICE) as ClipboardManager diff --git a/app/src/main/java/com/duckduckgo/app/pixels/remoteconfig/AndroidBrowserConfigFeature.kt b/app/src/main/java/com/duckduckgo/app/pixels/remoteconfig/AndroidBrowserConfigFeature.kt index cc6328142d2d..55375f6b24d4 100644 --- a/app/src/main/java/com/duckduckgo/app/pixels/remoteconfig/AndroidBrowserConfigFeature.kt +++ b/app/src/main/java/com/duckduckgo/app/pixels/remoteconfig/AndroidBrowserConfigFeature.kt @@ -83,4 +83,11 @@ interface AndroidBrowserConfigFeature { */ @Toggle.DefaultValue(false) fun featuresRequestHeader(): Toggle + + /** + * When enabled we should delete the app_webview/Default/Local Storage folder. If all goes well, we should not need to set this to `true` + * in remote config + */ + @Toggle.DefaultValue(false) + fun deleteLocalStorageKillSwitch(): Toggle }