diff --git a/CHANGELOG.md b/CHANGELOG.md index 8da32d65..ddb881e7 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -5,6 +5,7 @@ ### Features - Add `@SentrySnapshot` runtime annotation for configuring the per-snapshot diff threshold, published as `io.sentry:sentry-snapshots-runtime` ([EME-1055](https://linear.app/getsentry/issue/EME-1055)) +- Emit `diff_threshold` in the snapshot sidecar JSON when a `@Preview` is also annotated with `@SentrySnapshot(diffThreshold = ...)` ([EME-1055](https://linear.app/getsentry/issue/EME-1055)) ### Dependencies diff --git a/plugin-build/src/main/kotlin/io/sentry/android/gradle/snapshot/GenerateSnapshotTestsTask.kt b/plugin-build/src/main/kotlin/io/sentry/android/gradle/snapshot/GenerateSnapshotTestsTask.kt index b1ccf329..d0526fcb 100644 --- a/plugin-build/src/main/kotlin/io/sentry/android/gradle/snapshot/GenerateSnapshotTestsTask.kt +++ b/plugin-build/src/main/kotlin/io/sentry/android/gradle/snapshot/GenerateSnapshotTestsTask.kt @@ -376,6 +376,17 @@ class $CLASS_NAME( if (info.showSystemUi) metadata["show_system_ui"] = true if (info.showBackground) metadata["show_background"] = true + val diffThreshold: Float? = runCatching { + val declaring = Class.forName(preview.declaringClass) + val method = declaring.declaredMethods.firstOrNull { it.name == preview.methodName } + ?: return@runCatching null + @Suppress("UNCHECKED_CAST") + val annClass = Class.forName("io.sentry.snapshots.runtime.SentrySnapshot") as Class + val ann = method.getAnnotation(annClass) ?: return@runCatching null + annClass.getDeclaredMethod("diffThreshold").invoke(ann) as? Float + }.getOrNull() + if (diffThreshold != null && diffThreshold != 0f) metadata["diff_threshold"] = diffThreshold + val json = metadata.entries.joinToString(",\n ", prefix = "{\n ", postfix = "\n}") { (k, v) -> if (v is String) "\"" + k + "\": \"" + escapeJson(v) + "\"" else "\"" + k + "\": " + v diff --git a/plugin-build/src/test/kotlin/io/sentry/android/gradle/snapshot/GenerateSnapshotTestsTaskTest.kt b/plugin-build/src/test/kotlin/io/sentry/android/gradle/snapshot/GenerateSnapshotTestsTaskTest.kt index 31832fff..a93e6bad 100644 --- a/plugin-build/src/test/kotlin/io/sentry/android/gradle/snapshot/GenerateSnapshotTestsTaskTest.kt +++ b/plugin-build/src/test/kotlin/io/sentry/android/gradle/snapshot/GenerateSnapshotTestsTaskTest.kt @@ -126,6 +126,26 @@ class GenerateSnapshotTestsTaskTest { ) } + @Test + fun `generated sidecar reads SentrySnapshot annotation via reflection`() { + val content = generateAndRead(packageTrees = listOf("com.example")) + + assertTrue(content.contains("Class.forName(preview.declaringClass)")) + assertTrue(content.contains("\"io.sentry.snapshots.runtime.SentrySnapshot\"")) + assertTrue(content.contains("getDeclaredMethod(\"diffThreshold\")")) + } + + @Test + fun `generated sidecar emits diff_threshold only when non-default`() { + val content = generateAndRead(packageTrees = listOf("com.example")) + + assertTrue( + content.contains( + "if (diffThreshold != null && diffThreshold != 0f) metadata[\"diff_threshold\"] = diffThreshold" + ) + ) + } + @Test fun `parseMajorVersion extracts major from standard semver`() { assertEquals(1, parseMajorVersion("1.3.5"))