在线时间:8:00-16:00
迪恩网络APP
随时随地掌握行业动态
扫描二维码
关注迪恩网络微信公众号
开源软件名称(OpenSource Name):badoo/Reaktive开源软件地址(OpenSource Url):https://github.com/badoo/Reaktive开源编程语言(OpenSource Language):Kotlin 99.5%开源软件介绍(OpenSource Introduction):Kotlin multiplatform implementation of Reactive Extensions. Should you have any questions or feedback welcome to the Kotlin Slack channel: #reaktive SetupThere are a number of modules published to Maven Central:
Configuring dependencieskotlin {
sourceSets {
commonMain {
dependencies {
implementation 'com.badoo.reaktive:reaktive:<version>'
implementation 'com.badoo.reaktive:reaktive-annotations:<version>'
implementation 'com.badoo.reaktive:coroutines-interop:<version>' // For interop with coroutines
implementation 'com.badoo.reaktive:rxjava2-interop:<version>' // For interop with RxJava v2
implementation 'com.badoo.reaktive:rxjava3-interop:<version>' // For interop with RxJava v3
}
}
commonTest {
dependencies {
implementation 'com.badoo.reaktive:reaktive-testing:<version>'
}
}
}
} Features:
Reaktive and the old (strict) Kotlin/Native memory modelThe old (strict) Kotlin Native memory model and concurrency are very special. In general shared mutable state between threads is not allowed. Since Reaktive supports multithreading in Kotlin Native, please read the following documents before using it: Object detachment is relatively difficult to achieve and is very error-prone when the objects are created from outside and are not fully managed by the library. This is why Reaktive prefers frozen state. Here are some hints:
Thread local tricks to avoid freezingSometimes freezing is not acceptable, e.g. we might want to load some data in background and then update the UI. Obviously UI can not be frozen. With Reaktive it is possible to achieve such a behaviour in two ways: Use val values = mutableListOf<Any>()
var isFinished = false
observable<Any> { emitter ->
// Background job
}
.subscribeOn(ioScheduler)
.observeOn(mainScheduler)
.threadLocal()
.doOnBeforeNext { values += it } // Callback is not frozen, we can updated the mutable list
.doOnBeforeFinally { isFinished = true } // Callback is not frozen, we can change the flag
.subscribe() Set val values = mutableListOf<Any>()
var isComplete = false
observable<Any> { emitter ->
// Background job
}
.subscribeOn(ioScheduler)
.observeOn(mainScheduler)
.subscribe(
isThreadLocal = true,
onNext = { values += it }, // Callback is not frozen, we can updated the mutable list
onComplete = { isComplete = true } // Callback is not frozen, we can change the flag
) In both cases subscription ( Reaktive and the new (relaxed) Kotlin/Native memory modelThe new (relaxed) Kotlin/Native memory model
allows passing objects between threads without freezing. When using this memory model, there is no need
to use the Coroutines interopThis functionality is provided by the
Coroutines interop based on stable kotlinx.coroutinesThere are few important limitations:
Consider the following example for singleFromCoroutine {
// This block will be executed inside `runBlocking` in Kotlin/Native
}
.subscribeOn(ioScheduler) // Switching to a background thread is necessary
.observeOn(mainScheduler)
.subscribe { /* Get the result here */ } Please note that Ktor uses multi-threaded coroutines by default. If you are using Ktor, please use Coroutines interop based on multi-threaded kotlinx.coroutinesThe multi-threaded So there is one crucial difference - all Notes:
Coroutines interop general limitationsConverters Subscription management with DisposableScopeReaktive provides an easy way to manage subscriptions: DisposableScope. Take a look at the following examples: val scope =
disposableScope {
observable.subscribeScoped(...) // Subscription will be disposed when the scope is disposed
doOnDispose {
// Will be called when the scope is disposed
}
someDisposable.scope() // `someDisposable` will be disposed when the scope is disposed
}
// At some point later
scope.dispose() class MyPresenter(
private val view: MyView,
private val longRunningAction: Completable
) : DisposableScope by DisposableScope() {
init {
doOnDispose {
// Will be called when the presenter is disposed
}
}
fun load() {
view.showProgressBar()
// Subscription will be disposed when the presenter is disposed
longRunningAction.subscribeScoped(onComplete = view::hideProgressBar)
}
}
class MyActivity : AppCompatActivity(), DisposableScope by DisposableScope() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
MyPresenter(...).scope()
}
override fun onDestroy() {
dispose()
super.onDestroy()
}
} Reaktive and Swift interoperabilityPlease see the corresponding documentation page: Reaktive and Swift interoperability. Samples: |
2023-10-27
2022-08-15
2022-08-17
2022-09-23
2022-08-13
请发表评论