Skip to content

Commit

Permalink
a lot of improvements
Browse files Browse the repository at this point in the history
  • Loading branch information
InsanusMokrassar committed Nov 30, 2023
1 parent 44d35cf commit 4894a93
Show file tree
Hide file tree
Showing 13 changed files with 1,115 additions and 54 deletions.
7 changes: 7 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,13 @@

## 0.3.4

* `Core`:
* `Common`:
* Fixes in hierarchy saver/loader
* All `restoreHierarchy` extensions now not suspendable
* `JS`:
* Experimentally added `OneParameterUrlNavigationConfigsRepo`

## 0.3.3

* `MVVM`:
Expand Down
15 changes: 9 additions & 6 deletions core/src/commonMain/kotlin/extensions/Chain.kt
Original file line number Diff line number Diff line change
Expand Up @@ -8,12 +8,15 @@ import dev.inmo.navigation.core.*
import kotlinx.coroutines.flow.*

val <Base> NavigationChain<Base>.onNodesStackDiffFlow: Flow<Diff<NavigationNode<out Base, Base>>>
get() = flow {
var previous = stack
stackFlow.collect {
val newValue = stackFlow.value
emit(previous.diff(newValue, strictComparison = true))
previous = newValue
get() {
var previous = stack.toList()
return flow {
stackFlow.collect {
val newValue = stack
val diff = previous.diff(newValue, strictComparison = true)
emit(diff)
previous = newValue.toList()
}
}
}
val <Base> NavigationChain<Base>.onNodeAddedFlow
Expand Down
12 changes: 6 additions & 6 deletions core/src/commonMain/kotlin/repo/HierarchyHandler.kt
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ package dev.inmo.navigation.core.repo

import dev.inmo.navigation.core.*

suspend fun <Base> ConfigHolder.Chain<Base>.restoreHierarchy(
fun <Base> ConfigHolder.Chain<Base>.restoreHierarchy(
node: NavigationNode<out Base, Base>,
dropRedundantChainsOnRestores: Boolean = false
): NavigationChain<Base> {
Expand All @@ -13,7 +13,7 @@ suspend fun <Base> ConfigHolder.Chain<Base>.restoreHierarchy(
return subchain
}

suspend fun <Base> ConfigHolder.Chain<Base>.restoreHierarchy(
fun <Base> ConfigHolder.Chain<Base>.restoreHierarchy(
factory: NavigationNodeFactory<Base>,
chainToRestore: NavigationChain<Base> = NavigationChain(null, factory, id),
dropRedundantChainsOnRestores: Boolean = false
Expand All @@ -23,7 +23,7 @@ suspend fun <Base> ConfigHolder.Chain<Base>.restoreHierarchy(
return chainToRestore
}

suspend fun <Base> ConfigHolder.Node<Base>.restoreHierarchy(
fun <Base> ConfigHolder.Node<Base>.restoreHierarchy(
chain: NavigationChain<Base>,
dropRedundantChainsOnRestores: Boolean = false
): NavigationNode<out Base, Base>? {
Expand All @@ -48,7 +48,7 @@ suspend fun <Base> ConfigHolder.Node<Base>.restoreHierarchy(
return node
}

suspend fun <Base> NavigationChain<Base>.restoreHierarchy(
fun <Base> NavigationChain<Base>.restoreHierarchy(
holder: ConfigHolder.Node<Base>,
dropRedundantChainsOnRestores: Boolean = false
): NavigationNode<out Base, Base>? {
Expand All @@ -58,7 +58,7 @@ suspend fun <Base> NavigationChain<Base>.restoreHierarchy(
)
}

suspend fun <Base> NavigationNode<out Base, Base>.restoreHierarchy(
fun <Base> NavigationNode<out Base, Base>.restoreHierarchy(
holder: ConfigHolder.Chain<Base>,
dropRedundantChainsOnRestores: Boolean = false,
): NavigationChain<Base> {
Expand All @@ -68,7 +68,7 @@ suspend fun <Base> NavigationNode<out Base, Base>.restoreHierarchy(
)
}

suspend fun <T> restoreHierarchy(
fun <T> restoreHierarchy(
holder: ConfigHolder<T>,
factory: NavigationNodeFactory<T>,
rootChain: NavigationChain<T> = NavigationChain(null, factory),
Expand Down
10 changes: 5 additions & 5 deletions core/src/commonMain/kotlin/repo/HierarchyRepoUpdater.kt
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,6 @@ import dev.inmo.navigation.core.NavigationChain
import dev.inmo.navigation.core.NavigationNode
import dev.inmo.navigation.core.extensions.*
import kotlinx.coroutines.*
import kotlinx.coroutines.channels.BufferOverflow
import kotlinx.coroutines.flow.*

fun <T> NavigationConfigsRepo<T>.enableSavingHierarchy(
Expand Down Expand Up @@ -36,15 +35,16 @@ fun <T> NavigationConfigsRepo<T>.enableSavingHierarchy(
val currentSubscope = scope.LinkedSupervisorScope()
onNodesStackDiffFlow.filter { it.isEmpty() }.subscribeSafelyWithoutExceptions(currentSubscope) {
var needSave = false
needSave = it.added.any { it.value.storableInNavigationHierarchy } || needSave
needSave = it.replaced.any { it.first.value.storableInNavigationHierarchy || it.second.value.storableInNavigationHierarchy } || needSave
needSave = it.removed.any { it.value.storableInNavigationHierarchy } || needSave
needSave = needSave || it.added.any { it.value.storableInNavigationHierarchy }
needSave = needSave || it.replaced.any { it.first.value.storableInNavigationHierarchy || it.second.value.storableInNavigationHierarchy }
needSave = needSave || it.removed.any { it.value.storableInNavigationHierarchy }
if (needSave) {
save("initialization")
}
}
onNodeAddedFlow.flatten().subscribeSafelyWithoutExceptions(currentSubscope) { (_, newNode) ->
if (newNode.storableInNavigationHierarchy) {
val mustBeSaved = newNode.storableInNavigationHierarchy
if (mustBeSaved) {
save("node adding")
newNode.enableListeningUpdates(currentSubscope)
newNode.onChainAddedFlow.subscribeSafelyWithoutExceptions(scope) { newChains ->
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,56 @@
package dev.inmo.navigation.core.urls

import dev.inmo.kslog.common.taggedLogger
import dev.inmo.kslog.common.w
import dev.inmo.navigation.core.repo.ConfigHolder
import dev.inmo.navigation.core.repo.NavigationConfigsRepo
import kotlinx.browser.window
import kotlinx.serialization.KSerializer
import kotlinx.serialization.StringFormat
import org.w3c.dom.url.URLSearchParams

/**
* @param encodeDecoded Will be used when new navigation tree must be sent into navigation param.
* As a fact, the result of this callback will be inserted into url param
* @param decodeEncoded Will be used when repo will get value of navigation param to prepare it for
* [format]
*/
class OneParameterUrlNavigationConfigsRepo<T : Any>(
private val format: StringFormat,
private val configSerializer: KSerializer<T>,
private val queryParam: String = "navigation",
private val encodeDecoded: (String) -> String = { it },
private val decodeEncoded: (String) -> String = { it },
) : NavigationConfigsRepo<T> {
private val logger = taggedLogger(this)
private val serializer = ConfigHolder.serializer(configSerializer)
private val search: () -> URLSearchParams = {
URLSearchParams(window.location.search)
}

override fun save(holder: ConfigHolder<T>) {
val baseSearchQuery = search()
val stringToReplace = baseSearchQuery.toString()
val newEncodedState = encodeDecoded(format.encodeToString(serializer, holder))
baseSearchQuery.set(queryParam, newEncodedState)
val newQuery = baseSearchQuery.toString()
val newUrl = if (stringToReplace.isEmpty()) {
"${window.location.href}?${newQuery}"
} else {
window.location.href.replace(stringToReplace, newQuery)
}
window.history.pushState(
newEncodedState,
queryParam,
newUrl
)
}

override fun get(): ConfigHolder<T>? {
return runCatching {
format.decodeFromString(serializer, search().get(queryParam) ?.let(decodeEncoded) ?: return null)
}.onFailure {
logger.w(it) { "Unable to load navigation by param $queryParam from url" }
}.getOrNull()
}
}
16 changes: 0 additions & 16 deletions core/src/jsMain/kotlin/urls/UrlsNavigationConfigsRepo.kt

This file was deleted.

Loading

0 comments on commit 4894a93

Please sign in to comment.