From d88e5ae3c573cd16c7268163ad014edb38b33012 Mon Sep 17 00:00:00 2001 From: Josh Leibstein Date: Sun, 12 Jan 2025 19:05:16 +0000 Subject: [PATCH] Ensure LevelDB Iterator is closed (#5458) Task/Issue URL: https://app.asana.com/0/1200204095367872/1209128100809324/f ### Description - Closes the `DBIterator` after local storage has been cleared. - Also keeps the DB open and updates the DB initialization to be `Lazy`. ### Steps to test this PR _Filter logcat by WebLocalStorageManager_ - [x] Visit cnn.com - [x] Use the fire button - [x] Verify that cnn.com entries are deleted --- .../app/browser/weblocalstorage/WebLocalStorageManager.kt | 8 ++++---- .../app/browser/DuckDuckGoWebLocalStorageManagerTest.kt | 8 ++++---- 2 files changed, 8 insertions(+), 8 deletions(-) diff --git a/app/src/main/java/com/duckduckgo/app/browser/weblocalstorage/WebLocalStorageManager.kt b/app/src/main/java/com/duckduckgo/app/browser/weblocalstorage/WebLocalStorageManager.kt index ef4f52f4a761..94b1905237a0 100644 --- a/app/src/main/java/com/duckduckgo/app/browser/weblocalstorage/WebLocalStorageManager.kt +++ b/app/src/main/java/com/duckduckgo/app/browser/weblocalstorage/WebLocalStorageManager.kt @@ -21,13 +21,13 @@ import com.duckduckgo.app.pixels.remoteconfig.AndroidBrowserConfigFeature import com.duckduckgo.di.scopes.AppScope import com.squareup.anvil.annotations.ContributesBinding import com.squareup.anvil.annotations.ContributesTo +import dagger.Lazy import dagger.Module import dagger.Provides import dagger.SingleInstanceIn import java.io.File import java.nio.charset.StandardCharsets import javax.inject.Inject -import javax.inject.Provider import kotlinx.coroutines.runBlocking import org.iq80.leveldb.DB import org.iq80.leveldb.Options @@ -40,7 +40,7 @@ interface WebLocalStorageManager { @ContributesBinding(AppScope::class) class DuckDuckGoWebLocalStorageManager @Inject constructor( - private val databaseProvider: Provider, + private val databaseProvider: Lazy, private val androidBrowserConfigFeature: AndroidBrowserConfigFeature, private val webLocalStorageSettingsJsonParser: WebLocalStorageSettingsJsonParser, ) : WebLocalStorageManager { @@ -58,8 +58,8 @@ class DuckDuckGoWebLocalStorageManager @Inject constructor( Timber.d("WebLocalStorageManager: Allowed domains: $domains") Timber.d("WebLocalStorageManager: Matching regex: $matchingRegex") - databaseProvider.get().use { db -> - val iterator = db.iterator() + val db = databaseProvider.get() + db.iterator().use { iterator -> iterator.seekToFirst() while (iterator.hasNext()) { diff --git a/app/src/test/java/com/duckduckgo/app/browser/DuckDuckGoWebLocalStorageManagerTest.kt b/app/src/test/java/com/duckduckgo/app/browser/DuckDuckGoWebLocalStorageManagerTest.kt index 604d958ffd97..9ef2f6136224 100644 --- a/app/src/test/java/com/duckduckgo/app/browser/DuckDuckGoWebLocalStorageManagerTest.kt +++ b/app/src/test/java/com/duckduckgo/app/browser/DuckDuckGoWebLocalStorageManagerTest.kt @@ -23,7 +23,7 @@ import com.duckduckgo.app.browser.weblocalstorage.WebLocalStorageSettings import com.duckduckgo.app.browser.weblocalstorage.WebLocalStorageSettingsJsonParser import com.duckduckgo.app.pixels.remoteconfig.AndroidBrowserConfigFeature import com.duckduckgo.feature.toggles.api.Toggle -import javax.inject.Provider +import dagger.Lazy import kotlinx.coroutines.test.runTest import org.iq80.leveldb.DB import org.iq80.leveldb.DBIterator @@ -39,7 +39,7 @@ class DuckDuckGoWebLocalStorageManagerTest { private val mockDB: DB = mock() private val mockIterator: DBIterator = mock() - private val mockDatabaseProvider: Provider = mock() + private val mockDatabaseProvider: Lazy = mock() private val mockWebLocalStorageSettingsJsonParser: WebLocalStorageSettingsJsonParser = mock() private val mockAndroidBrowserConfigFeature: AndroidBrowserConfigFeature = mock() private val mockToggle: Toggle = mock() @@ -152,13 +152,13 @@ class DuckDuckGoWebLocalStorageManagerTest { } @Test - fun whenClearWebLocalStorageThenDBIsClosed() { + fun whenClearWebLocalStorageThenIteratorIsClosed() { whenever(mockDB.iterator()).thenReturn(mockIterator) whenever(mockIterator.hasNext()).thenReturn(false) testee.clearWebLocalStorage() - verify(mockDB).close() + verify(mockIterator).close() } private fun createMockDBEntry(key: ByteArray): MutableMap.MutableEntry {