diff --git a/.jules/bolt.md b/.jules/bolt.md new file mode 100644 index 0000000..357fbff --- /dev/null +++ b/.jules/bolt.md @@ -0,0 +1,3 @@ +## 2024-05-24 - WasmJs JSON Parsing Overhead +**Learning:** JSON decoding in Kotlin Multiplatform for WasmJs targets carries significant overhead, making repeated parsing of localStorage contents a performance bottleneck. +**Action:** Use an in-memory cache (e.g., via `by lazy`) to store parsed JSON structures and only sync to localStorage when necessary. diff --git a/halogen-engine/src/wasmJsMain/kotlin/halogen/engine/LocalStorageThemeCache.kt b/halogen-engine/src/wasmJsMain/kotlin/halogen/engine/LocalStorageThemeCache.kt index aba1f32..f38bc31 100644 --- a/halogen-engine/src/wasmJsMain/kotlin/halogen/engine/LocalStorageThemeCache.kt +++ b/halogen-engine/src/wasmJsMain/kotlin/halogen/engine/LocalStorageThemeCache.kt @@ -49,17 +49,21 @@ public class LocalStorageThemeCache( private val json = Json { ignoreUnknownKeys = true } private val manifestKey = "${prefix}__keys__" - // ── Manifest helpers ──────────────────────────────────────────────── - - private fun readManifest(): MutableSet { - val raw = jsGetItem(manifestKey.toJsString())?.toString() ?: return mutableSetOf() - return try { + private val cachedManifest: MutableSet by lazy { + val raw = jsGetItem(manifestKey.toJsString())?.toString() ?: return@lazy mutableSetOf() + try { json.decodeFromString>(raw).toMutableSet() } catch (_: Exception) { mutableSetOf() } } + // ── Manifest helpers ──────────────────────────────────────────────── + + private fun readManifest(): MutableSet { + return cachedManifest + } + private fun writeManifest(keys: Set) { val encoded = json.encodeToString(keys) jsSetItem(manifestKey.toJsString(), encoded.toJsString()) @@ -155,6 +159,7 @@ public class LocalStorageThemeCache( removeEntry("$prefix$key") } jsRemoveItem(manifestKey.toJsString()) + manifest.clear() _changes.tryEmit(CacheEvent.Cleared) }