Heyya! Does anyone know if/how I can store data on...
# webassembly
o
Heyya! Does anyone know if/how I can store data on web browser using wasmJs? Either a DB or a JSON file would be more than enough for me.
👀 1
a
There are some local variables like
localStorage
(for data to be stored "infinitely") and
sessionStorage
for the session (so, until user close your app): https://developer.mozilla.org/en-US/docs/Web/API/Window/sessionStorage They are key-value storage, so, you can store your data like this:
Copy code
external interface BrowserStorage {
  fun setItem(key: String, value: String)
  fun getItem(key: String): String?
  fun removeItem(key: String)
  fun clear()
}

external val localStorage: BrowserStorage
external val sessionStorage: BrowserStorage
So, you can use them like this:
Copy code
import kotlinx.serialization.Serializable
import kotlinx.serialization.encodeToString
import kotlinx.serialization.decodeFromString
import kotlinx.serialization.json.Json
import localStorage

@Serializable
data class User(val name: String, val age: Int)

fun main() {
  var user = User("Some User", 26)
  val jsonString = Json.encodeToString(user)
  localStorage.setItem("USER", jsonString)

  val savedUser = localStorage.getItem("USER") ?: error("User was not saved")
  user = Json.decodeFromString<User>(savedUser)
}
For more advanced DB-like experience there is a thing called IndexedDB: https://developer.mozilla.org/en-US/docs/Web/API/IndexedDB_API/Using_IndexedDB
o
Noice - thanks for this 🙂 Dumb follow-up question. As far as I understand wasmJS supports javascript interoperability. So can I use existing KotlinJS libraries (such as SQLDelight)? I've tried to import it in my wasmJsMain configuration but it says that the artifact cannot be found.
Copy code
wasmJsMain.dependencies {
            implementation("app.cash.sqldelight:web-worker-driver:2.0.2")
            implementation(devNpm("copy-webpack-plugin", "9.1.0"))
        }
a
No, right now, if a library has Kotlin/JS support it doesn't mean that it can be used in Kotlin/Wasm. The interop model is quite different of those two, so, unfortunately, we can't provide such an experience 😞 So, until the library authors don't add wasmJs as a target to their library, it couldn't be used in wasmJs project.
o
Alright. It obviously makes sense. Not a big deal as I just need something very obvious and straightforward. Thanks a lot for your time and patience.
🫡 1
e
> we can't provide such an experience Do you think at some point the compiler could be smart enough to generate the necessary external declarations from a K/JS klib, when importing it from K/WASM? Would definitely be pretty cool.
m
Does anybody have the correct mappings for using IndexedDB? I wonder why these are not generally available and have to be declared as external manually.
p
Not databases, but if you just need some type of persistence, there are a few libraries. Check these ones: https://github.com/russhwolf/multiplatform-settings https://github.com/Liftric/KVault https://github.com/xxfast/KStore
m
To my knowledge IndexedDB is the only technique to store substantial amounts of data in a browser.
p
I don't know what these libraries use under the hood. They are probably using that
e
@Michael Paus
IndexedDB
externals should go under https://github.com/Kotlin/kotlinx-browser I guess you can either open an issue there, or use YouTrack.
👍 3
Note that the name of the repository is a bit misleading, in the sense that one might think it's K/JS related, but it's WASM stuff.
kotlin-wrappers should also get
wasmJs
support at some point. I know there is an ongoing effort.
m
@Pablichjenkov They don’t. E.g. multiplatform-settings uses localStorage and is thus limited to a typical quota of just 5MB.
p
Ouch 🤕 I see. Thanks for this information
m
For a real storage solution OPFS is probably the way to go. You can read about the various quotas here: https://developer.mozilla.org/en-US/docs/Web/API/Storage_API/Storage_quotas_and_eviction_criteria
💡 1
a
You could probably use the web version of SQLite for this. https://sqlite.org/wasm/doc/trunk/demo-123.md
m
I am waiting for SQLDelight (which I am currently using anyway) to support that.
🥰 1
o
Same, would love to see it in action! 👍
155 Views