From 83ec8e35952192185d92b3650b70b02b672322ba Mon Sep 17 00:00:00 2001 From: Jordan Haven <117691317+jhaven-stytch@users.noreply.github.com> Date: Thu, 23 Jan 2025 13:49:48 -0500 Subject: [PATCH] Fix leaking webview in DFPProvider (#247) --- gradle/libs.versions.toml | 2 ++ .../java/com/stytch/sdk/common/dfp/DFPProvider.kt | 11 +++++++---- workbench-apps/b2b-workbench/build.gradle.kts | 1 + workbench-apps/consumer-workbench/build.gradle.kts | 2 ++ 4 files changed, 12 insertions(+), 4 deletions(-) diff --git a/gradle/libs.versions.toml b/gradle/libs.versions.toml index fd47fefa3..bdc80ffff 100644 --- a/gradle/libs.versions.toml +++ b/gradle/libs.versions.toml @@ -56,6 +56,7 @@ ktlint = "12.1.0" detekt = "1.23.6" ksp = "2.1.0-1.0.29" kotlinCompilerExtension="1.5.15" +leakCanary = "2.14" [libraries] activity = { module = "androidx.activity:activity", version.ref = "activityKtx" } @@ -134,6 +135,7 @@ flowRedux-jvm = { module = "com.freeletics.flowredux:flowredux-jvm", version.ref flowRedux-compose = { module = "com.freeletics.flowredux:compose", version.ref = "flowRedux" } coil-compose = { module = "io.coil-kt.coil3:coil-compose", version.ref = "coil" } coil-network = { module = "io.coil-kt.coil3:coil-network-okhttp", version.ref = "coil" } +leakCanary = { module = "com.squareup.leakcanary:leakcanary-android", version.ref = "leakCanary"} [plugins] androidApplication = { id = "com.android.application", version.ref = "gradle" } diff --git a/source/sdk/src/main/java/com/stytch/sdk/common/dfp/DFPProvider.kt b/source/sdk/src/main/java/com/stytch/sdk/common/dfp/DFPProvider.kt index 2b26d9a00..a9d287cdf 100644 --- a/source/sdk/src/main/java/com/stytch/sdk/common/dfp/DFPProvider.kt +++ b/source/sdk/src/main/java/com/stytch/sdk/common/dfp/DFPProvider.kt @@ -46,11 +46,14 @@ internal class DFPProviderImpl( object { @JavascriptInterface fun reportTelemetryId(telemetryId: String) { - activityProvider.currentActivity?.let { - it.runOnUiThread { - (webview.parent as? ViewGroup)?.removeView(webview) + activityProvider.currentActivity?.let { currentActivity -> + webview?.let { + currentActivity.runOnUiThread { + (it.parent as? ViewGroup)?.removeView(it) + } } } + webview = null if (continuation.isActive) { continuation.resume(telemetryId, null) } @@ -59,7 +62,7 @@ internal class DFPProviderImpl( private lateinit var continuation: CancellableContinuation - private lateinit var webview: WebView + private var webview: WebView? = null override suspend fun getTelemetryId(): String = suspendCancellableCoroutine { cont -> diff --git a/workbench-apps/b2b-workbench/build.gradle.kts b/workbench-apps/b2b-workbench/build.gradle.kts index 9e1b7f4bc..301ae5725 100644 --- a/workbench-apps/b2b-workbench/build.gradle.kts +++ b/workbench-apps/b2b-workbench/build.gradle.kts @@ -67,6 +67,7 @@ dependencies { testImplementation(libs.junit) androidTestImplementation(libs.androidx.junit) androidTestImplementation(libs.androidx.espresso.core) + debugImplementation(libs.leakCanary) // Compose implementation(platform(libs.compose.bom)) diff --git a/workbench-apps/consumer-workbench/build.gradle.kts b/workbench-apps/consumer-workbench/build.gradle.kts index a90787a84..bcdf318c6 100644 --- a/workbench-apps/consumer-workbench/build.gradle.kts +++ b/workbench-apps/consumer-workbench/build.gradle.kts @@ -71,6 +71,8 @@ dependencies { androidTestImplementation(libs.androidx.junit) androidTestImplementation(libs.androidx.espresso.core) + debugImplementation(libs.leakCanary) + // Compose implementation(platform(libs.compose.bom)) implementation(libs.ui)