From 2f2fa9b96c91c86ffa600b6707e1cca52ea398cd Mon Sep 17 00:00:00 2001 From: Rick Busarow Date: Sat, 11 Jul 2020 21:34:44 -0500 Subject: [PATCH 1/5] change LifecycleCoroutineScope argument to CoroutineContext --- ...ngCoroutineScopeRuleWithLifecycleSample.kt | 4 +- .../README.md | 8 +- .../dispatch-android-lifecycle-extensions.api | 1 + ...> LifecycleCoroutineScopeFactorySample.kt} | 16 +++- ...ScopeSample.kt => LifecycleScopeSample.kt} | 17 +--- .../lifecycle/LifecycleScopeFactory.kt | 65 ++++++++++---- .../internal/LifecycleCoroutineScopeStore.kt | 4 +- .../android/lifecycle/lifecycleScope.kt | 2 +- .../lifecycle/LifecycleScopeExtensionTest.kt | 9 +- .../lifecycle/LifecycleScopeFactoryTest.kt | 17 ++-- .../lifecycle/internal/AtomicGetOrPutTest.kt | 72 ++++++++-------- .../api/dispatch-android-lifecycle.api | 21 ++++- .../LifecycleCoroutineScopeFactorySample.kt | 52 ++++++++++++ .../samples/LifecycleCoroutineScopeSample.kt | 78 +++++++++++++++-- .../java/samples/LifecycleSuspendSample.kt | 2 +- .../lifecycle/LifecycleCoroutineScope.kt | 84 ++++++++++++++----- .../LifecycleCoroutineScopeFactory.kt | 40 +++++++++ .../LifecycleCoroutineScopeBinding.kt | 16 ++-- ...LifecycleScopeExt.kt => lifecycleScope.kt} | 0 .../{LifecycleSuspendExt.kt => suspend.kt} | 24 +++--- 20 files changed, 385 insertions(+), 147 deletions(-) rename dispatch-android-lifecycle-extensions/samples/src/test/java/samples/{LifecycleScopeFactorySample.kt => LifecycleCoroutineScopeFactorySample.kt} (72%) rename dispatch-android-lifecycle-extensions/samples/src/test/java/samples/{LifecycleCoroutineScopeSample.kt => LifecycleScopeSample.kt} (81%) create mode 100644 dispatch-android-lifecycle/samples/src/test/java/samples/LifecycleCoroutineScopeFactorySample.kt create mode 100644 dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleCoroutineScopeFactory.kt rename dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/internal/{LifecycleScopeExt.kt => lifecycleScope.kt} (100%) rename dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/{LifecycleSuspendExt.kt => suspend.kt} (78%) diff --git a/dispatch-android-espresso/samples/src/test/java/samples/IdlingCoroutineScopeRuleWithLifecycleSample.kt b/dispatch-android-espresso/samples/src/test/java/samples/IdlingCoroutineScopeRuleWithLifecycleSample.kt index a3587ab13..7f9b983b9 100644 --- a/dispatch-android-espresso/samples/src/test/java/samples/IdlingCoroutineScopeRuleWithLifecycleSample.kt +++ b/dispatch-android-espresso/samples/src/test/java/samples/IdlingCoroutineScopeRuleWithLifecycleSample.kt @@ -39,9 +39,7 @@ class IdlingCoroutineScopeRuleWithLifecycleSample { @Before fun setUp() { - LifecycleScopeFactory.set { - MainImmediateCoroutineScope(customDispatcherProvider) - } + LifecycleScopeFactory.set { customDispatcherProvider } ViewModelScopeFactory.set { MainImmediateCoroutineScope(customDispatcherProvider) } diff --git a/dispatch-android-lifecycle-extensions/README.md b/dispatch-android-lifecycle-extensions/README.md index 3a7ad72fd..80cd46feb 100644 --- a/dispatch-android-lifecycle-extensions/README.md +++ b/dispatch-android-lifecycle-extensions/README.md @@ -51,7 +51,7 @@ class SomeApplication : Application() { override fun onCreate() { super.onCreate() // A custom factory can be set to add elements to the CoroutineContext - LifecycleScopeFactory.set { MainImmediateCoroutineScope() + SomeCustomElement() } + LifecycleScopeFactory.set { MainImmediateProvidedCoroutineContext() + SomeCustomElement() } } } ``` @@ -62,13 +62,13 @@ class SomeEspressoTest { fun setUp() { // This custom factory can be used to use custom scopes for testing, // such as an idling dispatcher - LifecycleScopeFactory.set { MainImmediateIdlingCoroutineScope() } + LifecycleScopeFactory.set { MainImmediateIdlingCoroutineScope().coroutineContext } } @After fun tearDown() { // The factory can also be reset to default - LifecycleScopeFactory.reset() + LifecycleCoroutineScopeFactory.reset() } } ``` @@ -93,7 +93,7 @@ class SomeFragmentEspressoTest { fun setUp() { // set a custom factory which is applied to all newly created lifecycleScopes LifecycleScopeFactory.set { - MainImmediateCoroutineScope() + idlingRule.dispatcherProvider + MainImmediateProvidedCoroutineContext() + idlingRule.dispatcherProvider } // now SomeFragment will use an IdlingDispatcher in its CoroutineScope diff --git a/dispatch-android-lifecycle-extensions/api/dispatch-android-lifecycle-extensions.api b/dispatch-android-lifecycle-extensions/api/dispatch-android-lifecycle-extensions.api index e3d8b4c1b..4b5a29cae 100644 --- a/dispatch-android-lifecycle-extensions/api/dispatch-android-lifecycle-extensions.api +++ b/dispatch-android-lifecycle-extensions/api/dispatch-android-lifecycle-extensions.api @@ -1,6 +1,7 @@ public final class dispatch/android/lifecycle/LifecycleScopeFactory { public static final field INSTANCE Ldispatch/android/lifecycle/LifecycleScopeFactory; public final fun reset ()V + public final fun set (Ldispatch/android/lifecycle/LifecycleCoroutineScopeFactory;)V public final fun set (Lkotlin/jvm/functions/Function0;)V } diff --git a/dispatch-android-lifecycle-extensions/samples/src/test/java/samples/LifecycleScopeFactorySample.kt b/dispatch-android-lifecycle-extensions/samples/src/test/java/samples/LifecycleCoroutineScopeFactorySample.kt similarity index 72% rename from dispatch-android-lifecycle-extensions/samples/src/test/java/samples/LifecycleScopeFactorySample.kt rename to dispatch-android-lifecycle-extensions/samples/src/test/java/samples/LifecycleCoroutineScopeFactorySample.kt index a76259164..1fa6c07d5 100644 --- a/dispatch-android-lifecycle-extensions/samples/src/test/java/samples/LifecycleScopeFactorySample.kt +++ b/dispatch-android-lifecycle-extensions/samples/src/test/java/samples/LifecycleCoroutineScopeFactorySample.kt @@ -20,6 +20,7 @@ package samples import dispatch.android.espresso.* import dispatch.android.lifecycle.* import dispatch.core.* +import kotlinx.coroutines.* class LifecycleScopeFactorySample { @@ -29,7 +30,8 @@ class LifecycleScopeFactorySample { class MyApplication : Application { override fun onCreate() { - LifecycleScopeFactory.set { MainImmediateCoroutineScope() } + + LifecycleScopeFactory.set { MyCustomElement() + MainImmediateProvidedContext() } } } } @@ -41,19 +43,25 @@ class LifecycleScopeFactorySample { @Before fun setUp() { - LifecycleScopeFactory.set { MainImmediateIdlingCoroutineScope() } + + val dispatcherProvider = IdlingDispatcherProvider() + + LifecycleScopeFactory.set { SupervisorJob() + dispatcherProvider + dispatcherProvider.mainImmediate } } } } @Sample - fun lifecycleScopeFactoryResetSample() { + fun LifecycleScopeFactoryResetSample() { class MyEspressoTest { @Before fun setUp() { - LifecycleScopeFactory.set { MainImmediateIdlingCoroutineScope() } + + val dispatcherProvider = DefaultDispatcherProvider() + + LifecycleScopeFactory.set { SupervisorJob() + dispatcherProvider + dispatcherProvider.mainImmediate } } @After diff --git a/dispatch-android-lifecycle-extensions/samples/src/test/java/samples/LifecycleCoroutineScopeSample.kt b/dispatch-android-lifecycle-extensions/samples/src/test/java/samples/LifecycleScopeSample.kt similarity index 81% rename from dispatch-android-lifecycle-extensions/samples/src/test/java/samples/LifecycleCoroutineScopeSample.kt rename to dispatch-android-lifecycle-extensions/samples/src/test/java/samples/LifecycleScopeSample.kt index 0761c8f54..3fda9662c 100644 --- a/dispatch-android-lifecycle-extensions/samples/src/test/java/samples/LifecycleCoroutineScopeSample.kt +++ b/dispatch-android-lifecycle-extensions/samples/src/test/java/samples/LifecycleScopeSample.kt @@ -17,24 +17,11 @@ package samples import dispatch.android.lifecycle.* import dispatch.core.* -import dispatch.test.* -import kotlinx.coroutines.* -import org.junit.jupiter.api.* -@CoroutineTest -@ExperimentalCoroutinesApi -class LifecycleCoroutineScopeSample( - val testScope: TestProvidedCoroutineScope -) { - - @BeforeEach - fun beforeEach() { - - LifecycleScopeFactory.set { testScope } - } +class LifecycleScopeSample { @Sample - fun lifecycleCoroutineScopeSample() { + fun lifecycleScopeSample() { // This could be any LifecycleOwner -- Fragments, Activities, Services... class SomeFragment : Fragment() { diff --git a/dispatch-android-lifecycle-extensions/src/main/java/dispatch/android/lifecycle/LifecycleScopeFactory.kt b/dispatch-android-lifecycle-extensions/src/main/java/dispatch/android/lifecycle/LifecycleScopeFactory.kt index cc52175b8..5523c4c14 100644 --- a/dispatch-android-lifecycle-extensions/src/main/java/dispatch/android/lifecycle/LifecycleScopeFactory.kt +++ b/dispatch-android-lifecycle-extensions/src/main/java/dispatch/android/lifecycle/LifecycleScopeFactory.kt @@ -15,48 +15,85 @@ package dispatch.android.lifecycle -import androidx.lifecycle.* import dispatch.android.lifecycle.LifecycleScopeFactory.reset import dispatch.core.* +import kotlinx.coroutines.* +import kotlin.coroutines.* /** * Factory holder for [LifecycleCoroutineScope]'s. * - * By default, `create` returns a [MainImmediateCoroutineScope]. + * By default, `create` returns a [MainImmediateProvidedContext]. * * This factory can be overridden for testing or to include a custom [CoroutineContext][kotlin.coroutines.CoroutineContext] - * in production code. This may be done in [Application.onCreate][android.app.Application.onCreate] + * in production code. This may be done in [Application.onCreate][android.app.Application.onCreate], + * or else as early as possible in the Application's existence. + * + * A custom factory will persist for the application's full lifecycle unless overwritten or [reset]. * * [reset] may be used to reset the factory to default at any time. + * + * @see MainImmediateProvidedContext + * @see LifecycleCoroutineScope + * @see LifecycleCoroutineScopeFactory * @sample samples.LifecycleScopeFactorySample.setLifecycleScopeFactoryProductionSample * @sample samples.LifecycleScopeFactorySample.setLifecycleScopeFactoryEspressoSample */ -public object LifecycleScopeFactory { +object LifecycleScopeFactory { + + private val defaultFactory: LifecycleCoroutineScopeFactory + get() = LifecycleCoroutineScopeFactory { MainImmediateProvidedContext() } - private var _factory: () -> MainImmediateCoroutineScope = { MainImmediateCoroutineScope() } + private var factoryInstance = defaultFactory + + internal fun get() = factoryInstance + + /** + * Immediately resets the factory function to its default. + * + * @sample samples.LifecycleScopeFactorySample.LifecycleScopeFactoryResetSample + */ + @Suppress("UNUSED") + public fun reset() { + factoryInstance = defaultFactory + } /** * Override the default [MainImmediateCoroutineScope] factory, for testing or to include a custom [CoroutineContext][kotlin.coroutines.CoroutineContext] * in production code. This may be done in [Application.onCreate][android.app.Application.onCreate] * - * @param factory sets a custom [MainImmediateCoroutineScope] factory to be used for all new instance creations until reset. + * @param factory sets a custom [CoroutineContext] factory to be used for all new instance creations until reset. + * Its [Elements][CoroutineContext.Element] will be re-used, except: + * 1. If a [DispatcherProvider] element isn't present, a [DefaultDispatcherProvider] will be added. + * 2. If a [Job] element isn't present, a [SupervisorJob] will be added. + * 3. If the [ContinuationInterceptor][kotlin.coroutines.ContinuationInterceptor] does not match + * the one referenced by the [possibly new] [DispatcherProvider.mainImmediate] property, it will be updated to match. * * @sample samples.LifecycleScopeFactorySample.setLifecycleScopeFactoryProductionSample * @sample samples.LifecycleScopeFactorySample.setLifecycleScopeFactoryEspressoSample */ - public fun set(factory: () -> MainImmediateCoroutineScope) { - _factory = factory + @Suppress("UNUSED") + public fun set(factory: LifecycleCoroutineScopeFactory) { + factoryInstance = factory } - internal fun create(lifecycle: Lifecycle) = LifecycleCoroutineScope(lifecycle, _factory.invoke()) - /** - * Immediately resets the factory function to its default. + * Override the default [MainImmediateCoroutineScope] factory, for testing or to include a custom [CoroutineContext][kotlin.coroutines.CoroutineContext] + * in production code. This may be done in [Application.onCreate][android.app.Application.onCreate] * - * @sample samples.LifecycleScopeFactorySample.lifecycleScopeFactoryResetSample + * @param factory sets a custom [CoroutineContext] factory to be used for all new instance creations until reset. + * Its [Elements][CoroutineContext.Element] will be re-used, except: + * 1. If a [DispatcherProvider] element isn't present, a [DefaultDispatcherProvider] will be added. + * 2. If a [Job] element isn't present, a [SupervisorJob] will be added. + * 3. If the [ContinuationInterceptor][kotlin.coroutines.ContinuationInterceptor] does not match + * the one referenced by the [possibly new] [DispatcherProvider.mainImmediate] property, it will be updated to match. + * + * @sample samples.LifecycleScopeFactorySample.setLifecycleScopeFactoryProductionSample + * @sample samples.LifecycleScopeFactorySample.setLifecycleScopeFactoryEspressoSample */ - public fun reset() { - _factory = { MainImmediateCoroutineScope() } + @Suppress("UNUSED") + public fun set(factory: () -> CoroutineContext) { + factoryInstance = LifecycleCoroutineScopeFactory(factory) } } diff --git a/dispatch-android-lifecycle-extensions/src/main/java/dispatch/android/lifecycle/internal/LifecycleCoroutineScopeStore.kt b/dispatch-android-lifecycle-extensions/src/main/java/dispatch/android/lifecycle/internal/LifecycleCoroutineScopeStore.kt index ec5f6d1d4..6c57465a6 100644 --- a/dispatch-android-lifecycle-extensions/src/main/java/dispatch/android/lifecycle/internal/LifecycleCoroutineScopeStore.kt +++ b/dispatch-android-lifecycle-extensions/src/main/java/dispatch/android/lifecycle/internal/LifecycleCoroutineScopeStore.kt @@ -41,7 +41,7 @@ internal object LifecycleCoroutineScopeStore : LifecycleEventObserver { fun get(lifecycle: Lifecycle): LifecycleCoroutineScope { if (lifecycle.currentState <= Lifecycle.State.DESTROYED) { - return LifecycleScopeFactory.create(lifecycle) + return LifecycleScopeFactory.get().create(lifecycle) } return when { @@ -65,7 +65,7 @@ internal object LifecycleCoroutineScopeStore : LifecycleEventObserver { private fun bindLifecycle(lifecycle: Lifecycle): LifecycleCoroutineScope { - val scope = LifecycleScopeFactory.create(lifecycle) + val scope = LifecycleScopeFactory.get().create(lifecycle) scope.launchMainImmediate { if (lifecycle.currentState >= Lifecycle.State.INITIALIZED) { diff --git a/dispatch-android-lifecycle-extensions/src/main/java/dispatch/android/lifecycle/lifecycleScope.kt b/dispatch-android-lifecycle-extensions/src/main/java/dispatch/android/lifecycle/lifecycleScope.kt index d8e112ac9..9fbcf64e6 100644 --- a/dispatch-android-lifecycle-extensions/src/main/java/dispatch/android/lifecycle/lifecycleScope.kt +++ b/dispatch-android-lifecycle-extensions/src/main/java/dispatch/android/lifecycle/lifecycleScope.kt @@ -31,7 +31,7 @@ import kotlinx.coroutines.* * The `viewModelScope` is automatically cancelled when the [LifecycleOwner]'s * [lifecycle][LifecycleOwner.getLifecycle]'s [Lifecycle.State] drops to [Lifecycle.State.DESTROYED]. * - * @sample samples.LifecycleCoroutineScopeSample.lifecycleCoroutineScopeSample + * @sample samples.LifecycleScopeSample.lifecycleScopeSample */ val LifecycleOwner.lifecycleScope: LifecycleCoroutineScope get() = LifecycleCoroutineScopeStore.get(this.lifecycle) diff --git a/dispatch-android-lifecycle-extensions/src/test/java/dispatch/android/lifecycle/LifecycleScopeExtensionTest.kt b/dispatch-android-lifecycle-extensions/src/test/java/dispatch/android/lifecycle/LifecycleScopeExtensionTest.kt index 4ece68490..5fcfa3678 100644 --- a/dispatch-android-lifecycle-extensions/src/test/java/dispatch/android/lifecycle/LifecycleScopeExtensionTest.kt +++ b/dispatch-android-lifecycle-extensions/src/test/java/dispatch/android/lifecycle/LifecycleScopeExtensionTest.kt @@ -40,17 +40,12 @@ internal class LifecycleScopeExtensionTest : HermitJUnit5() { val dispatcher = TestCoroutineDispatcher() - LifecycleScopeFactory.set { - TestProvidedCoroutineScope( - dispatcher, - TestDispatcherProvider(dispatcher), - Job() - ) - } + LifecycleScopeFactory.set { dispatcher + TestDispatcherProvider(dispatcher) + Job() } } @AfterEach fun afterEach() { + LifecycleScopeFactory.reset() storeMap.clear() } diff --git a/dispatch-android-lifecycle-extensions/src/test/java/dispatch/android/lifecycle/LifecycleScopeFactoryTest.kt b/dispatch-android-lifecycle-extensions/src/test/java/dispatch/android/lifecycle/LifecycleScopeFactoryTest.kt index b9bae6a37..9395aba11 100644 --- a/dispatch-android-lifecycle-extensions/src/test/java/dispatch/android/lifecycle/LifecycleScopeFactoryTest.kt +++ b/dispatch-android-lifecycle-extensions/src/test/java/dispatch/android/lifecycle/LifecycleScopeFactoryTest.kt @@ -45,6 +45,7 @@ internal class LifecycleScopeFactoryTest : HermitJUnit5() { @BeforeAll fun beforeAll() { + LifecycleScopeFactory.reset() Dispatchers.setMain(mainDispatcher) } @@ -59,25 +60,23 @@ internal class LifecycleScopeFactoryTest : HermitJUnit5() { } @Test - fun `default factory should be a default MainImmediateCoroutineScope`() = runBlockingTest { + fun `default factory should be a default MainImmediateProvidedContext`() = runBlockingTest { - val scope = LifecycleScopeFactory.create(lifecycleOwner.lifecycle) + val scope = LifecycleScopeFactory.get().create(lifecycleOwner.lifecycle) scope.coroutineContext[DispatcherProvider]!!.shouldBeTypeOf() scope.coroutineContext[Job]!!.shouldBeSupervisorJob() scope.coroutineContext[ContinuationInterceptor] shouldBe Dispatchers.Main - - scope.shouldBeInstanceOf() } @Test fun `a custom factory should be used after being set`() = runBlockingTest { - LifecycleScopeFactory.set { MainImmediateCoroutineScope(originContext) } + LifecycleScopeFactory.set { originContext } - val scope = LifecycleScopeFactory.create(lifecycleOwner.lifecycle) + val scope = LifecycleScopeFactory.get().create(lifecycleOwner.lifecycle) scope.coroutineContext shouldEqualFolded originContext + mainDispatcher } @@ -85,15 +84,15 @@ internal class LifecycleScopeFactoryTest : HermitJUnit5() { @Test fun `reset after setting a custom factory should return to the default`() = runBlockingTest { - LifecycleScopeFactory.set { MainImmediateCoroutineScope(originContext) } + LifecycleScopeFactory.set { originContext } - val custom = LifecycleScopeFactory.create(lifecycleOwner.lifecycle) + val custom = LifecycleScopeFactory.get().create(lifecycleOwner.lifecycle) custom.coroutineContext shouldEqualFolded originContext + mainDispatcher LifecycleScopeFactory.reset() - val default = LifecycleScopeFactory.create(lifecycleOwner.lifecycle) + val default = LifecycleScopeFactory.get().create(lifecycleOwner.lifecycle) default.coroutineContext[DispatcherProvider]!!.shouldBeTypeOf() diff --git a/dispatch-android-lifecycle-extensions/src/test/java/dispatch/android/lifecycle/internal/AtomicGetOrPutTest.kt b/dispatch-android-lifecycle-extensions/src/test/java/dispatch/android/lifecycle/internal/AtomicGetOrPutTest.kt index 5a39884e7..9bd190416 100644 --- a/dispatch-android-lifecycle-extensions/src/test/java/dispatch/android/lifecycle/internal/AtomicGetOrPutTest.kt +++ b/dispatch-android-lifecycle-extensions/src/test/java/dispatch/android/lifecycle/internal/AtomicGetOrPutTest.kt @@ -20,69 +20,67 @@ import dispatch.android.lifecycle.LifecycleCoroutineScope import dispatch.core.* import dispatch.internal.test.android.* import dispatch.test.* -import io.kotest.core.spec.* -import io.kotest.core.spec.style.* +import hermit.test.junit.* import io.kotest.matchers.* import kotlinx.coroutines.* +import org.junit.jupiter.api.* import java.util.concurrent.* @ObsoleteCoroutinesApi @ExperimentalCoroutinesApi -internal class AtomicGetOrPutTest : BehaviorSpec() { +internal class AtomicGetOrPutTest : HermitJUnit5() { - override fun isolationMode(): IsolationMode? = IsolationMode.InstancePerTest + @Nested + inner class `API level 23` { - init { + @Nested + inner class `multiple threads access lifecycleScope at once` { + @Test + fun `all threads should get the same instance`() = runBlocking { - given("API level 23") { + val main = newSingleThreadContext("main") - `when`("multiple threads access lifecycleScope at once") { + val storeMap = ConcurrentHashMap() - then("all threads should get the same instance").config(invocations = 10) { + val lifecycleOwner = FakeLifecycleOwner(Lifecycle.State.INITIALIZED) - val main = newSingleThreadContext("main") + val androidLifecycle = lifecycleOwner.lifecycle - val storeMap = ConcurrentHashMap() + val hugeExecutor = ThreadPoolExecutor( + 200, 200, 5000, TimeUnit.MILLISECONDS, LinkedBlockingQueue() + ).asCoroutineDispatcher() - val lifecycleOwner = FakeLifecycleOwner(Lifecycle.State.INITIALIZED) + val lock = CompletableDeferred() - val androidLifecycle = lifecycleOwner.lifecycle + val all = List(200) { + async(hugeExecutor) { - val hugeExecutor = ThreadPoolExecutor( - 200, 200, 5000, TimeUnit.MILLISECONDS, LinkedBlockingQueue() - ).asCoroutineDispatcher() + lock.await() - val lock = CompletableDeferred() + storeMap.atomicGetOrPut(androidLifecycle) { + val scope = LifecycleCoroutineScope( + lifecycle = androidLifecycle, + coroutineScope = MainImmediateCoroutineScope(Job(), TestDispatcherProvider(main)) + ) + withContext(main) { - val all = List(200) { - async(hugeExecutor) { - - lock.await() - - storeMap.atomicGetOrPut(androidLifecycle) { - val scope = LifecycleCoroutineScope( - lifecycle = androidLifecycle, - coroutineScope = MainImmediateCoroutineScope(Job(), TestDispatcherProvider(main)) - ) - withContext(main) { - - androidLifecycle.addObserver(LifecycleCoroutineScopeStore) - } - scope + androidLifecycle.addObserver(LifecycleCoroutineScopeStore) } + scope } } + } - yield() - lock.complete(Unit) + yield() + lock.complete(Unit) - all.awaitAll().distinct().size shouldBe 1 + all.awaitAll().distinct().size shouldBe 1 - delay(100) + delay(100) - androidLifecycle.observerCount shouldBe 2 - } + androidLifecycle.observerCount shouldBe 2 } + } } } diff --git a/dispatch-android-lifecycle/api/dispatch-android-lifecycle.api b/dispatch-android-lifecycle/api/dispatch-android-lifecycle.api index 886eb7de1..e8448f7ce 100644 --- a/dispatch-android-lifecycle/api/dispatch-android-lifecycle.api +++ b/dispatch-android-lifecycle/api/dispatch-android-lifecycle.api @@ -7,8 +7,10 @@ public final class dispatch/android/lifecycle/BuildConfig { public fun ()V } -public final class dispatch/android/lifecycle/LifecycleCoroutineScope : dispatch/core/MainImmediateCoroutineScope { - public fun (Landroidx/lifecycle/Lifecycle;Ldispatch/core/MainImmediateCoroutineScope;)V +public class dispatch/android/lifecycle/LifecycleCoroutineScope : dispatch/core/MainImmediateCoroutineScope { + public static final field Companion Ldispatch/android/lifecycle/LifecycleCoroutineScope$Companion; + public fun (Landroidx/lifecycle/Lifecycle;Lkotlin/coroutines/CoroutineContext;)V + public synthetic fun (Landroidx/lifecycle/Lifecycle;Lkotlin/coroutines/CoroutineContext;ILkotlin/jvm/internal/DefaultConstructorMarker;)V public fun getCoroutineContext ()Lkotlin/coroutines/CoroutineContext; public final fun getLifecycle ()Landroidx/lifecycle/Lifecycle; public final fun launchOnCreate (Ldispatch/android/lifecycle/LifecycleCoroutineScope$MinimumStatePolicy;Lkotlin/jvm/functions/Function2;)Lkotlinx/coroutines/Job; @@ -19,6 +21,10 @@ public final class dispatch/android/lifecycle/LifecycleCoroutineScope : dispatch public static synthetic fun launchOnStart$default (Ldispatch/android/lifecycle/LifecycleCoroutineScope;Ldispatch/android/lifecycle/LifecycleCoroutineScope$MinimumStatePolicy;Lkotlin/jvm/functions/Function2;ILjava/lang/Object;)Lkotlinx/coroutines/Job; } +public final class dispatch/android/lifecycle/LifecycleCoroutineScope$Companion { + public final fun invoke (Landroidx/lifecycle/Lifecycle;Lkotlinx/coroutines/CoroutineScope;)Ldispatch/android/lifecycle/LifecycleCoroutineScope; +} + public final class dispatch/android/lifecycle/LifecycleCoroutineScope$MinimumStatePolicy : java/lang/Enum { public static final field CANCEL Ldispatch/android/lifecycle/LifecycleCoroutineScope$MinimumStatePolicy; public static final field RESTART_EVERY Ldispatch/android/lifecycle/LifecycleCoroutineScope$MinimumStatePolicy; @@ -26,7 +32,16 @@ public final class dispatch/android/lifecycle/LifecycleCoroutineScope$MinimumSta public static fun values ()[Ldispatch/android/lifecycle/LifecycleCoroutineScope$MinimumStatePolicy; } -public final class dispatch/android/lifecycle/LifecycleSuspendExtKt { +public final class dispatch/android/lifecycle/LifecycleCoroutineScopeFactory { + public fun (Lkotlin/jvm/functions/Function0;)V + public final fun create (Landroidx/lifecycle/Lifecycle;)Ldispatch/android/lifecycle/LifecycleCoroutineScope; +} + +public final class dispatch/android/lifecycle/LifecycleCoroutineScopeKt { + public static final fun MainImmediateProvidedContext ()Lkotlin/coroutines/CoroutineContext; +} + +public final class dispatch/android/lifecycle/SuspendKt { public static final fun onNextCreate (Landroidx/lifecycle/Lifecycle;Lkotlin/jvm/functions/Function2;Lkotlin/coroutines/Continuation;)Ljava/lang/Object; public static final fun onNextCreate (Landroidx/lifecycle/LifecycleOwner;Lkotlin/jvm/functions/Function2;Lkotlin/coroutines/Continuation;)Ljava/lang/Object; public static final fun onNextResume (Landroidx/lifecycle/Lifecycle;Lkotlin/jvm/functions/Function2;Lkotlin/coroutines/Continuation;)Ljava/lang/Object; diff --git a/dispatch-android-lifecycle/samples/src/test/java/samples/LifecycleCoroutineScopeFactorySample.kt b/dispatch-android-lifecycle/samples/src/test/java/samples/LifecycleCoroutineScopeFactorySample.kt new file mode 100644 index 000000000..c2e7d3a82 --- /dev/null +++ b/dispatch-android-lifecycle/samples/src/test/java/samples/LifecycleCoroutineScopeFactorySample.kt @@ -0,0 +1,52 @@ +/* + * Copyright (C) 2020 Rick Busarow + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +@file:Suppress("EXPERIMENTAL_API_USAGE") + +package samples + +import dispatch.android.lifecycle.* + +class LifecycleCoroutineScopeFactorySample { + + @Sample + fun factorySample() { + + @Provides + fun provideFactory(): LifecycleCoroutineScopeFactory = + LifecycleCoroutineScopeFactory { + // other elements are added automatically + MyCustomElement() + } + + class MyFragment @Inject constructor( + factory: LifecycleCoroutineScopeFactory + ) : Fragment() { + + val lifecycleScope = factory.create(lifecycle) + + init { + lifecycleScope.launchOnStart { + // ... + } + } + } + } +} + +private annotation class Before +private annotation class After +private annotation class Module +private annotation class Provides diff --git a/dispatch-android-lifecycle/samples/src/test/java/samples/LifecycleCoroutineScopeSample.kt b/dispatch-android-lifecycle/samples/src/test/java/samples/LifecycleCoroutineScopeSample.kt index 2ee8efd46..6e3b0423f 100644 --- a/dispatch-android-lifecycle/samples/src/test/java/samples/LifecycleCoroutineScopeSample.kt +++ b/dispatch-android-lifecycle/samples/src/test/java/samples/LifecycleCoroutineScopeSample.kt @@ -23,7 +23,8 @@ import io.kotest.matchers.* import kotlinx.coroutines.* import kotlinx.coroutines.channels.* import kotlinx.coroutines.flow.* -import org.junit.jupiter.api.* + +annotation class Inject @CoroutineTest @ExperimentalCoroutinesApi @@ -31,30 +32,60 @@ class LifecycleCoroutineScopeSample( val testScope: TestProvidedCoroutineScope ) { - @BeforeEach - fun beforeEach() { + @Sample + fun lifecycleCoroutineScopeFromScopeSample() = runBlocking { + + // This could be any LifecycleOwner -- Fragments, Activities, Services... + class SomeFragment @Inject constructor( + coroutineScope: CoroutineScope // could be any type of CoroutineScope + ) : Fragment() { + + val lifecycleScope = LifecycleCoroutineScope(lifecycle, coroutineScope) + + init { + + // active only when "resumed". starts a fresh coroutine each time + lifecycleScope.launchOnResume { } + + // active only when "started". starts a fresh coroutine each time + // this is a rough proxy for LiveData behavior + lifecycleScope.launchOnStart { } - LifecycleScopeFactory.set { testScope } + // active after only the first "started" event, and never re-started + lifecycleScope.launchOnStart(minimumStatePolicy = CANCEL) { } + + // launch when created, automatically stop on destroy + lifecycleScope.launchOnCreate { } + + // it works as a normal CoroutineScope as well (because it is) + lifecycleScope.launchMain { } + + } + } } @Sample - fun lifecycleCoroutineScopeSample() = runBlocking { + fun lifecycleCoroutineScopeFromContextSample() = runBlocking { // This could be any LifecycleOwner -- Fragments, Activities, Services... class SomeFragment : Fragment() { - init { + val context = Job() + DispatcherProvider() - // auto-created MainImmediateCoroutineScope which is lifecycle-aware - lifecycleScope //... + val lifecycleScope = LifecycleCoroutineScope(lifecycle, context) + + init { // active only when "resumed". starts a fresh coroutine each time - // this is a rough proxy for LiveData behavior lifecycleScope.launchOnResume { } // active only when "started". starts a fresh coroutine each time + // this is a rough proxy for LiveData behavior lifecycleScope.launchOnStart { } + // active after only the first "started" event, and never re-started + lifecycleScope.launchOnStart(minimumStatePolicy = CANCEL) { } + // launch when created, automatically stop on destroy lifecycleScope.launchOnCreate { } @@ -65,6 +96,35 @@ class LifecycleCoroutineScopeSample( } } + @Sample + fun lifecycleCoroutineScopeDefaultSample() = runBlocking { + + // This could be any LifecycleOwner -- Fragments, Activities, Services... + class SomeFragment : Fragment() { + + val lifecycleScope = LifecycleCoroutineScope(lifecycle) + + init { + + // active only when "resumed". starts a fresh coroutine each time + lifecycleScope.launchOnResume { } + + // active only when "started". starts a fresh coroutine each time + // this is a rough proxy for LiveData behavior + lifecycleScope.launchOnStart { } + + // active after only the first "started" event, and never re-started + lifecycleScope.launchOnStart(minimumStatePolicy = CANCEL) { } + + // launch when created, automatically stop on destroy + lifecycleScope.launchOnCreate { } + + // it works as a normal CoroutineScope as well (because it is) + lifecycleScope.launchMain { } + } + } + } + @Sample fun launchOnCreateOnceSample() = runBlocking { diff --git a/dispatch-android-lifecycle/samples/src/test/java/samples/LifecycleSuspendSample.kt b/dispatch-android-lifecycle/samples/src/test/java/samples/LifecycleSuspendSample.kt index 8260a398e..412486fbf 100644 --- a/dispatch-android-lifecycle/samples/src/test/java/samples/LifecycleSuspendSample.kt +++ b/dispatch-android-lifecycle/samples/src/test/java/samples/LifecycleSuspendSample.kt @@ -31,7 +31,7 @@ class LifecycleSuspendSample( @BeforeEach fun beforeEach() { - LifecycleScopeFactory.set { testScope } + LifecycleScopeFactory.set { testScope.coroutineContext } } @Sample diff --git a/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleCoroutineScope.kt b/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleCoroutineScope.kt index cf82a8b36..52e68183e 100644 --- a/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleCoroutineScope.kt +++ b/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleCoroutineScope.kt @@ -19,39 +19,56 @@ import androidx.lifecycle.* import dispatch.android.lifecycle.internal.* import dispatch.core.* import kotlinx.coroutines.* -import java.util.concurrent.CancellationException +import kotlin.coroutines.* /** - * [MainImmediateCoroutineScope] instance which is tied to a [Lifecycle]. + * Default implementation of a [CoroutineContext] as seen in a `MainImmediateCoroutineScope`. + * + * @see MainImmediateCoroutineScope + */ +public fun MainImmediateProvidedContext(): CoroutineContext { + val dispatcherProvider = DefaultDispatcherProvider() + + return SupervisorJob() + dispatcherProvider + dispatcherProvider.mainImmediate +} + +/** + * [MainImmediateCoroutineScope] which is tied to a [Lifecycle]. * * The [CoroutineScope] provides lifecycle-aware [launch] functions * which will automatically start upon reaching their associated [Lifecycle.Event], - * then automatically cancel upon the [lifecycle] dropping below that state. Reaching + * then automatically cancel upon the lifecycle dropping below that state. Reaching * that state again will start a new [Job]. * - * If this `CoroutineScope` has a [Job], it will be cancelled automatically - * as soon as the [lifecycle] reaches [DESTROYED][Lifecycle.State.DESTROYED]. + * This `CoroutineScope`'s [Job] will be cancelled automatically + * as soon as the `lifecycle` reaches [DESTROYED][Lifecycle.State.DESTROYED]. * - * @sample samples.LifecycleCoroutineScopeSample.lifecycleCoroutineScopeSample + * @sample samples.LifecycleCoroutineScopeSample.lifecycleCoroutineScopeDefaultSample + * @sample samples.LifecycleCoroutineScopeSample.lifecycleCoroutineScopeFromContextSample * @param lifecycle the lifecycle to which this [MainImmediateCoroutineScope] is linked. + * @param coroutineContext the source CoroutineContext which will be converted to a [MainImmediateCoroutineScope]. + * Its [Elements][CoroutineContext.Element] will be re-used, except: + * 1. If a [DispatcherProvider] element isn't present, a [DefaultDispatcherProvider] will be added. + * 2. If a [Job] element isn't present, a [SupervisorJob] will be added. + * 3. If the [ContinuationInterceptor][kotlin.coroutines.ContinuationInterceptor] does not match the one referenced by the [possibly new] [DispatcherProvider.mainImmediate] property, it will be updated to match. */ -class LifecycleCoroutineScope( +open class LifecycleCoroutineScope( val lifecycle: Lifecycle, - private val coroutineScope: MainImmediateCoroutineScope -) : MainImmediateCoroutineScope by coroutineScope { + coroutineContext: CoroutineContext = MainImmediateProvidedContext() +) : MainImmediateCoroutineScope by MainImmediateCoroutineScope(coroutineContext) { init { - LifecycleCoroutineScopeBinding(lifecycle, coroutineScope).bind() + LifecycleCoroutineScopeBinding(lifecycle, coroutineContext).bind() } /** * Lifecycle-aware function for launching a coroutine any time the [Lifecycle.State] * is at least [Lifecycle.State.CREATED]. * - * [block] is executed using the receiver [CoroutineScope]'s [Job] as a parent, + * `block` is executed using the receiver [CoroutineScope]'s [Job] as a parent, * but always executes using [Dispatchers.Main] as its [CoroutineDispatcher]. * - * Execution of [block] is cancelled when the receiver [CoroutineScope] is cancelled, + * Execution of `block` is cancelled when the receiver [CoroutineScope] is cancelled, * or when [lifecycle]'s [Lifecycle.State] drops below [Lifecycle.State.CREATED]. * * @param minimumStatePolicy *optional* - the way this [Job] will behave when passing below the minimum @@ -71,10 +88,10 @@ class LifecycleCoroutineScope( * Lifecycle-aware function for launching a coroutine any time the [Lifecycle.State] * is at least [Lifecycle.State.STARTED]. * - * [block] is executed using the receiver [CoroutineScope]'s [Job] as a parent, + * `block` is executed using the receiver [CoroutineScope]'s [Job] as a parent, * but always executes using [Dispatchers.Main] as its [CoroutineDispatcher]. * - * Execution of [block] is cancelled when the receiver [CoroutineScope] is cancelled, + * Execution of `block` is cancelled when the receiver [CoroutineScope] is cancelled, * or when [lifecycle]'s [Lifecycle.State] drops below [Lifecycle.State.STARTED]. * * @param minimumStatePolicy *optional* - the way this [Job] will behave when passing below the minimum @@ -91,10 +108,10 @@ class LifecycleCoroutineScope( * Lifecycle-aware function for launching a coroutine any time the [Lifecycle.State] * is at least [Lifecycle.State.RESUMED]. * - * [block] is executed using the receiver [CoroutineScope]'s [Job] as a parent, + * `block` is executed using the receiver [CoroutineScope]'s [Job] as a parent, * but always executes using [Dispatchers.Main] as its [CoroutineDispatcher]. * - * Execution of [block] is cancelled when the receiver [CoroutineScope] is cancelled, + * Execution of `block` is cancelled when the receiver [CoroutineScope] is cancelled, * or when [lifecycle]'s [Lifecycle.State] drops below [Lifecycle.State.RESUMED]. * * @param minimumStatePolicy *optional* - the way this [Job] will behave when passing below the minimum @@ -136,9 +153,34 @@ class LifecycleCoroutineScope( */ RESTART_EVERY } -} -internal class LifecycleCancellationException( - lifecycle: Lifecycle, - minimumState: Lifecycle.State -) : CancellationException("Lifecycle $lifecycle dropped below minimum state: $minimumState") + companion object { + + /** + * [MainImmediateCoroutineScope] which is tied to a [Lifecycle]. + * + * The [CoroutineScope] provides lifecycle-aware [launch] functions + * which will automatically start upon reaching their associated [Lifecycle.Event], + * then automatically cancel upon the lifecycle dropping below that state. Reaching + * that state again will start a new [Job]. + * + * If this `CoroutineScope` has a [Job], it will be cancelled automatically + * as soon as the `lifecycle` reaches [DESTROYED][Lifecycle.State.DESTROYED]. + * + * @sample samples.LifecycleCoroutineScopeSample.lifecycleCoroutineScopeFromScopeSample + * @param lifecycle the lifecycle to which this [MainImmediateCoroutineScope] is linked. + * @param coroutineScope the source CoroutineScope which will be converted to a [MainImmediateCoroutineScope]. + * Its [CoroutineContext][kotlin.coroutines.CoroutineContext] will be re-used, except: + * 1. If a [DispatcherProvider] element isn't present, a [DefaultDispatcherProvider] will be added. + * 2. If a [Job] element isn't present, a [SupervisorJob] will be added. + * 3. If the [ContinuationInterceptor][kotlin.coroutines.ContinuationInterceptor] does not match the one referenced by the [possibly new] [DispatcherProvider.mainImmediate] property, it will be updated to match. + */ + operator fun invoke( + lifecycle: Lifecycle, + coroutineScope: CoroutineScope + ): LifecycleCoroutineScope = LifecycleCoroutineScope( + lifecycle, coroutineScope.coroutineContext + ) + + } +} diff --git a/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleCoroutineScopeFactory.kt b/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleCoroutineScopeFactory.kt new file mode 100644 index 000000000..036dbf02f --- /dev/null +++ b/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleCoroutineScopeFactory.kt @@ -0,0 +1,40 @@ +/* + * Copyright (C) 2020 Rick Busarow + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package dispatch.android.lifecycle + +import androidx.lifecycle.* +import kotlin.coroutines.* + +/** + * Factory for [LifecycleCoroutineScope]s. This may be injected into a lifecycle-aware class + * to provide custom [CoroutineContexts][CoroutineContext]. + * + * @sample samples.LifecycleCoroutineScopeFactorySample.factorySample + * @param coroutineContextFactory the lambda defining the creating of a [CoroutineContext] + */ +public class LifecycleCoroutineScopeFactory( + private val coroutineContextFactory: () -> CoroutineContext +) { + + /** + * Creates a new [LifecycleCoroutineScope] using `coroutineContextFactory` + * + * @param lifecycle the lifecycle which will be bound to the [LifecycleCoroutineScope] + */ + public fun create( + lifecycle: Lifecycle + ): LifecycleCoroutineScope = LifecycleCoroutineScope(lifecycle, coroutineContextFactory.invoke()) +} diff --git a/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/internal/LifecycleCoroutineScopeBinding.kt b/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/internal/LifecycleCoroutineScopeBinding.kt index db44b7c65..58ecb9c61 100644 --- a/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/internal/LifecycleCoroutineScopeBinding.kt +++ b/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/internal/LifecycleCoroutineScopeBinding.kt @@ -16,13 +16,14 @@ package dispatch.android.lifecycle.internal import androidx.lifecycle.* -import dispatch.android.lifecycle.* import dispatch.core.* import kotlinx.coroutines.* +import java.util.concurrent.CancellationException +import kotlin.coroutines.* internal class LifecycleCoroutineScopeBinding( private val lifecycle: Lifecycle, - private val coroutineScope: CoroutineScope + private val coroutineContext: CoroutineContext ) : LifecycleEventObserver { fun bind() { @@ -30,7 +31,7 @@ internal class LifecycleCoroutineScopeBinding( if (lifecycle.currentState == Lifecycle.State.DESTROYED) { cancelDestroyed() } else { - coroutineScope.launchMainImmediate { + CoroutineScope(coroutineContext).launchMainImmediate { if (lifecycle.currentState == Lifecycle.State.DESTROYED) { cancelDestroyed() @@ -39,14 +40,14 @@ internal class LifecycleCoroutineScopeBinding( } } } - coroutineScope.coroutineContext[Job]?.invokeOnCompletion { + coroutineContext[Job]?.invokeOnCompletion { lifecycle.removeObserver(this) } } private fun cancelDestroyed() { lifecycle.removeObserver(this) - coroutineScope.coroutineContext.cancel( + coroutineContext.cancel( LifecycleCancellationException( lifecycle = lifecycle, minimumState = Lifecycle.State.INITIALIZED @@ -60,3 +61,8 @@ internal class LifecycleCoroutineScopeBinding( } } } + +internal class LifecycleCancellationException( + lifecycle: Lifecycle, + minimumState: Lifecycle.State +) : CancellationException("Lifecycle $lifecycle dropped below minimum state: $minimumState") diff --git a/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/internal/LifecycleScopeExt.kt b/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/internal/lifecycleScope.kt similarity index 100% rename from dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/internal/LifecycleScopeExt.kt rename to dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/internal/lifecycleScope.kt diff --git a/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleSuspendExt.kt b/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/suspend.kt similarity index 78% rename from dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleSuspendExt.kt rename to dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/suspend.kt index 54bc3aedf..1aa4f7880 100644 --- a/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleSuspendExt.kt +++ b/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/suspend.kt @@ -20,9 +20,9 @@ import dispatch.android.lifecycle.internal.* import kotlinx.coroutines.* /** - * Executes [block] one time, the next time the [Lifecycle]'s state is at least [Lifecycle.State.CREATED]. + * Executes `block` one time, the next time the [Lifecycle]'s state is at least [Lifecycle.State.CREATED]. * - * If the lifecycle is already in this state, [block] will be executed immediately. + * If the lifecycle is already in this state, `block` will be executed immediately. * * @see [LifecycleCoroutineScope.launchOnCreate] for repeating behavior. * @sample samples.LifecycleSuspendSample.lifecycleOwnerOnNextCreateSample @@ -32,9 +32,9 @@ suspend fun LifecycleOwner.onNextCreate( ): T? = lifecycle.onNext(Lifecycle.State.CREATED, block) /** - * Executes [block] one time, the next time the [Lifecycle]'s state is at least [Lifecycle.State.CREATED]. + * Executes `block` one time, the next time the [Lifecycle]'s state is at least [Lifecycle.State.CREATED]. * - * If the lifecycle is already in this state, [block] will be executed immediately. + * If the lifecycle is already in this state, `block` will be executed immediately. * * @see [LifecycleCoroutineScope.launchOnCreate] for repeating behavior. * @sample samples.LifecycleSuspendSample.lifecycleOnNextCreateSample @@ -44,9 +44,9 @@ suspend fun Lifecycle.onNextCreate( ): T? = onNext(Lifecycle.State.CREATED, block) /** - * Executes [block] one time, the next time the [Lifecycle]'s state is at least [Lifecycle.State.STARTED]. + * Executes `block` one time, the next time the [Lifecycle]'s state is at least [Lifecycle.State.STARTED]. * - * If the lifecycle is already in this state, [block] will be executed immediately. + * If the lifecycle is already in this state, `block` will be executed immediately. * * @see [LifecycleCoroutineScope.launchOnStart] for repeating behavior. * @sample samples.LifecycleSuspendSample.lifecycleOwnerOnNextStartSample @@ -56,9 +56,9 @@ suspend fun LifecycleOwner.onNextStart( ): T? = lifecycle.onNext(Lifecycle.State.STARTED, block) /** - * Executes [block] one time, the next time the [Lifecycle]'s state is at least [Lifecycle.State.STARTED]. + * Executes `block` one time, the next time the [Lifecycle]'s state is at least [Lifecycle.State.STARTED]. * - * If the lifecycle is already in this state, [block] will be executed immediately. + * If the lifecycle is already in this state, `block` will be executed immediately. * * @see [LifecycleCoroutineScope.launchOnStart] for repeating behavior. * @sample samples.LifecycleSuspendSample.lifecycleOnNextStartSample @@ -68,9 +68,9 @@ suspend fun Lifecycle.onNextStart( ): T? = onNext(Lifecycle.State.STARTED, block) /** - * Executes [block] one time, the next time the [Lifecycle]'s state is at least [Lifecycle.State.RESUMED]. + * Executes `block` one time, the next time the [Lifecycle]'s state is at least [Lifecycle.State.RESUMED]. * - * If the lifecycle is already in this state, [block] will be executed immediately. + * If the lifecycle is already in this state, `block` will be executed immediately. * * @see [LifecycleCoroutineScope.launchOnResume] for repeating behavior. * @sample samples.LifecycleSuspendSample.lifecycleOwnerOnNextResumeSample @@ -80,9 +80,9 @@ suspend fun LifecycleOwner.onNextResume( ): T? = lifecycle.onNext(Lifecycle.State.RESUMED, block) /** - * Executes [block] one time, the next time the [Lifecycle]'s state is at least [Lifecycle.State.RESUMED]. + * Executes `block` one time, the next time the [Lifecycle]'s state is at least [Lifecycle.State.RESUMED]. * - * If the lifecycle is already in this state, [block] will be executed immediately. + * If the lifecycle is already in this state, `block` will be executed immediately. * * @see [LifecycleCoroutineScope.launchOnResume] for repeating behavior. * @sample samples.LifecycleSuspendSample.lifecycleOnNextResumeSample From 15d0db60619e204ed11176ac459f804f136aed70 Mon Sep 17 00:00:00 2001 From: Rick Busarow Date: Sat, 11 Jul 2020 21:37:15 -0500 Subject: [PATCH 2/5] MainImmediateProvidedContext -> MainImmediateContext --- .../java/samples/LifecycleCoroutineScopeFactorySample.kt | 2 +- .../dispatch/android/lifecycle/LifecycleScopeFactory.kt | 6 +++--- .../dispatch/android/lifecycle/LifecycleCoroutineScope.kt | 4 ++-- 3 files changed, 6 insertions(+), 6 deletions(-) diff --git a/dispatch-android-lifecycle-extensions/samples/src/test/java/samples/LifecycleCoroutineScopeFactorySample.kt b/dispatch-android-lifecycle-extensions/samples/src/test/java/samples/LifecycleCoroutineScopeFactorySample.kt index 1fa6c07d5..9b8f9891e 100644 --- a/dispatch-android-lifecycle-extensions/samples/src/test/java/samples/LifecycleCoroutineScopeFactorySample.kt +++ b/dispatch-android-lifecycle-extensions/samples/src/test/java/samples/LifecycleCoroutineScopeFactorySample.kt @@ -31,7 +31,7 @@ class LifecycleScopeFactorySample { override fun onCreate() { - LifecycleScopeFactory.set { MyCustomElement() + MainImmediateProvidedContext() } + LifecycleScopeFactory.set { MyCustomElement() + MainImmediateContext() } } } } diff --git a/dispatch-android-lifecycle-extensions/src/main/java/dispatch/android/lifecycle/LifecycleScopeFactory.kt b/dispatch-android-lifecycle-extensions/src/main/java/dispatch/android/lifecycle/LifecycleScopeFactory.kt index 5523c4c14..9c08a9ee7 100644 --- a/dispatch-android-lifecycle-extensions/src/main/java/dispatch/android/lifecycle/LifecycleScopeFactory.kt +++ b/dispatch-android-lifecycle-extensions/src/main/java/dispatch/android/lifecycle/LifecycleScopeFactory.kt @@ -23,7 +23,7 @@ import kotlin.coroutines.* /** * Factory holder for [LifecycleCoroutineScope]'s. * - * By default, `create` returns a [MainImmediateProvidedContext]. + * By default, `create` returns a [MainImmediateContext]. * * This factory can be overridden for testing or to include a custom [CoroutineContext][kotlin.coroutines.CoroutineContext] * in production code. This may be done in [Application.onCreate][android.app.Application.onCreate], @@ -33,7 +33,7 @@ import kotlin.coroutines.* * * [reset] may be used to reset the factory to default at any time. * - * @see MainImmediateProvidedContext + * @see MainImmediateContext * @see LifecycleCoroutineScope * @see LifecycleCoroutineScopeFactory * @sample samples.LifecycleScopeFactorySample.setLifecycleScopeFactoryProductionSample @@ -42,7 +42,7 @@ import kotlin.coroutines.* object LifecycleScopeFactory { private val defaultFactory: LifecycleCoroutineScopeFactory - get() = LifecycleCoroutineScopeFactory { MainImmediateProvidedContext() } + get() = LifecycleCoroutineScopeFactory { MainImmediateContext() } private var factoryInstance = defaultFactory diff --git a/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleCoroutineScope.kt b/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleCoroutineScope.kt index 52e68183e..29eb2185d 100644 --- a/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleCoroutineScope.kt +++ b/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleCoroutineScope.kt @@ -26,7 +26,7 @@ import kotlin.coroutines.* * * @see MainImmediateCoroutineScope */ -public fun MainImmediateProvidedContext(): CoroutineContext { +public fun MainImmediateContext(): CoroutineContext { val dispatcherProvider = DefaultDispatcherProvider() return SupervisorJob() + dispatcherProvider + dispatcherProvider.mainImmediate @@ -54,7 +54,7 @@ public fun MainImmediateProvidedContext(): CoroutineContext { */ open class LifecycleCoroutineScope( val lifecycle: Lifecycle, - coroutineContext: CoroutineContext = MainImmediateProvidedContext() + coroutineContext: CoroutineContext = MainImmediateContext() ) : MainImmediateCoroutineScope by MainImmediateCoroutineScope(coroutineContext) { init { From 13fda8b04094e3f47657cb009db05cde89c0ab56 Mon Sep 17 00:00:00 2001 From: Rick Busarow Date: Sat, 11 Jul 2020 21:43:27 -0500 Subject: [PATCH 3/5] MainImmediateProvidedContext -> MainImmediateContext --- .../dispatch/android/lifecycle/LifecycleScopeFactory.kt | 4 +++- .../lifecycle/internal/LifecycleCoroutineScopeStore.kt | 4 ++-- .../android/lifecycle/LifecycleScopeFactoryTest.kt | 8 ++++---- .../api/dispatch-android-lifecycle.api | 2 +- 4 files changed, 10 insertions(+), 8 deletions(-) diff --git a/dispatch-android-lifecycle-extensions/src/main/java/dispatch/android/lifecycle/LifecycleScopeFactory.kt b/dispatch-android-lifecycle-extensions/src/main/java/dispatch/android/lifecycle/LifecycleScopeFactory.kt index 9c08a9ee7..615483bc5 100644 --- a/dispatch-android-lifecycle-extensions/src/main/java/dispatch/android/lifecycle/LifecycleScopeFactory.kt +++ b/dispatch-android-lifecycle-extensions/src/main/java/dispatch/android/lifecycle/LifecycleScopeFactory.kt @@ -15,6 +15,7 @@ package dispatch.android.lifecycle +import androidx.lifecycle.* import dispatch.android.lifecycle.LifecycleScopeFactory.reset import dispatch.core.* import kotlinx.coroutines.* @@ -46,7 +47,8 @@ object LifecycleScopeFactory { private var factoryInstance = defaultFactory - internal fun get() = factoryInstance + internal fun create(lifecycle: Lifecycle): LifecycleCoroutineScope = + factoryInstance.create(lifecycle) /** * Immediately resets the factory function to its default. diff --git a/dispatch-android-lifecycle-extensions/src/main/java/dispatch/android/lifecycle/internal/LifecycleCoroutineScopeStore.kt b/dispatch-android-lifecycle-extensions/src/main/java/dispatch/android/lifecycle/internal/LifecycleCoroutineScopeStore.kt index 6c57465a6..ec5f6d1d4 100644 --- a/dispatch-android-lifecycle-extensions/src/main/java/dispatch/android/lifecycle/internal/LifecycleCoroutineScopeStore.kt +++ b/dispatch-android-lifecycle-extensions/src/main/java/dispatch/android/lifecycle/internal/LifecycleCoroutineScopeStore.kt @@ -41,7 +41,7 @@ internal object LifecycleCoroutineScopeStore : LifecycleEventObserver { fun get(lifecycle: Lifecycle): LifecycleCoroutineScope { if (lifecycle.currentState <= Lifecycle.State.DESTROYED) { - return LifecycleScopeFactory.get().create(lifecycle) + return LifecycleScopeFactory.create(lifecycle) } return when { @@ -65,7 +65,7 @@ internal object LifecycleCoroutineScopeStore : LifecycleEventObserver { private fun bindLifecycle(lifecycle: Lifecycle): LifecycleCoroutineScope { - val scope = LifecycleScopeFactory.get().create(lifecycle) + val scope = LifecycleScopeFactory.create(lifecycle) scope.launchMainImmediate { if (lifecycle.currentState >= Lifecycle.State.INITIALIZED) { diff --git a/dispatch-android-lifecycle-extensions/src/test/java/dispatch/android/lifecycle/LifecycleScopeFactoryTest.kt b/dispatch-android-lifecycle-extensions/src/test/java/dispatch/android/lifecycle/LifecycleScopeFactoryTest.kt index 9395aba11..19acb1f9d 100644 --- a/dispatch-android-lifecycle-extensions/src/test/java/dispatch/android/lifecycle/LifecycleScopeFactoryTest.kt +++ b/dispatch-android-lifecycle-extensions/src/test/java/dispatch/android/lifecycle/LifecycleScopeFactoryTest.kt @@ -62,7 +62,7 @@ internal class LifecycleScopeFactoryTest : HermitJUnit5() { @Test fun `default factory should be a default MainImmediateProvidedContext`() = runBlockingTest { - val scope = LifecycleScopeFactory.get().create(lifecycleOwner.lifecycle) + val scope = LifecycleScopeFactory.create(lifecycleOwner.lifecycle) scope.coroutineContext[DispatcherProvider]!!.shouldBeTypeOf() @@ -76,7 +76,7 @@ internal class LifecycleScopeFactoryTest : HermitJUnit5() { LifecycleScopeFactory.set { originContext } - val scope = LifecycleScopeFactory.get().create(lifecycleOwner.lifecycle) + val scope = LifecycleScopeFactory.create(lifecycleOwner.lifecycle) scope.coroutineContext shouldEqualFolded originContext + mainDispatcher } @@ -86,13 +86,13 @@ internal class LifecycleScopeFactoryTest : HermitJUnit5() { LifecycleScopeFactory.set { originContext } - val custom = LifecycleScopeFactory.get().create(lifecycleOwner.lifecycle) + val custom = LifecycleScopeFactory.create(lifecycleOwner.lifecycle) custom.coroutineContext shouldEqualFolded originContext + mainDispatcher LifecycleScopeFactory.reset() - val default = LifecycleScopeFactory.get().create(lifecycleOwner.lifecycle) + val default = LifecycleScopeFactory.create(lifecycleOwner.lifecycle) default.coroutineContext[DispatcherProvider]!!.shouldBeTypeOf() diff --git a/dispatch-android-lifecycle/api/dispatch-android-lifecycle.api b/dispatch-android-lifecycle/api/dispatch-android-lifecycle.api index e8448f7ce..29119d195 100644 --- a/dispatch-android-lifecycle/api/dispatch-android-lifecycle.api +++ b/dispatch-android-lifecycle/api/dispatch-android-lifecycle.api @@ -38,7 +38,7 @@ public final class dispatch/android/lifecycle/LifecycleCoroutineScopeFactory { } public final class dispatch/android/lifecycle/LifecycleCoroutineScopeKt { - public static final fun MainImmediateProvidedContext ()Lkotlin/coroutines/CoroutineContext; + public static final fun MainImmediateContext ()Lkotlin/coroutines/CoroutineContext; } public final class dispatch/android/lifecycle/SuspendKt { From 598ab783db22e5fc9d8804d7550008534d26dd87 Mon Sep 17 00:00:00 2001 From: Rick Busarow Date: Sat, 11 Jul 2020 21:46:19 -0500 Subject: [PATCH 4/5] update docs --- .../-init-.md | 4 +- .../-idling-dispatcher-provider-rule/index.md | 4 +- .../-lifecycle-scope-factory/index.md | 27 ++++++-- .../-lifecycle-scope-factory/reset.md | 7 ++- .../-lifecycle-scope-factory/set.md | 14 +++-- .../androidx.fragment.app.-fragment/index.md | 7 --- .../with-view-lifecycle-scope.md | 31 ---------- .../index.md | 8 +-- .../alltypes/index.md | 10 ++- .../-init-.md | 34 +++++++++++ .../create.md | 11 ++++ .../index.md | 46 ++++++++++++++ .../-lifecycle-coroutine-scope/-init-.md | 55 ++++++++++++++--- .../-minimum-state-policy/-c-a-n-c-e-l.md | 2 +- .../-r-e-s-t-a-r-t_-e-v-e-r-y.md | 2 +- .../-minimum-state-policy/index.md | 2 +- .../-lifecycle-coroutine-scope/index.md | 61 ++++++++++++++++--- .../-lifecycle-coroutine-scope/invoke.md | 55 +++++++++++++++++ .../launch-on-create.md | 6 +- .../launch-on-resume.md | 6 +- .../launch-on-start.md | 6 +- .../-lifecycle-coroutine-scope/lifecycle.md | 2 +- .../-main-immediate-context.md | 12 ++++ .../-view-lifecycle-coroutine-scope/index.md | 15 ----- .../launch-on-create.md | 12 ---- .../launch-on-resume.md | 12 ---- .../launch-on-start.md | 12 ---- .../index.md | 6 +- .../on-next-create.md | 6 +- .../on-next-resume.md | 6 +- .../on-next-start.md | 6 +- .../androidx.lifecycle.-lifecycle/index.md | 6 +- .../on-next-create.md | 6 +- .../on-next-resume.md | 6 +- .../on-next-start.md | 6 +- .../dispatch.android.lifecycle/index.md | 9 ++- .../index.md | 7 --- .../with-view-lifecycle.md | 27 -------- .../dispatch-android-lifecycle-extensions.md | 8 +-- 39 files changed, 356 insertions(+), 206 deletions(-) delete mode 100644 docs/kdoc/dispatch-android-lifecycle-extensions/dispatch.android.lifecycle/androidx.fragment.app.-fragment/index.md delete mode 100644 docs/kdoc/dispatch-android-lifecycle-extensions/dispatch.android.lifecycle/androidx.fragment.app.-fragment/with-view-lifecycle-scope.md create mode 100644 docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope-factory/-init-.md create mode 100644 docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope-factory/create.md create mode 100644 docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope-factory/index.md create mode 100644 docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/invoke.md create mode 100644 docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-main-immediate-context.md delete mode 100644 docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-view-lifecycle-coroutine-scope/index.md delete mode 100644 docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-view-lifecycle-coroutine-scope/launch-on-create.md delete mode 100644 docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-view-lifecycle-coroutine-scope/launch-on-resume.md delete mode 100644 docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-view-lifecycle-coroutine-scope/launch-on-start.md delete mode 100644 docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/kotlinx.coroutines.-coroutine-scope/index.md delete mode 100644 docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/kotlinx.coroutines.-coroutine-scope/with-view-lifecycle.md diff --git a/docs/kdoc/dispatch-android-espresso/dispatch.android.espresso/-idling-dispatcher-provider-rule/-init-.md b/docs/kdoc/dispatch-android-espresso/dispatch.android.espresso/-idling-dispatcher-provider-rule/-init-.md index d3618c171..9f826b4dd 100644 --- a/docs/kdoc/dispatch-android-espresso/dispatch.android.espresso/-idling-dispatcher-provider-rule/-init-.md +++ b/docs/kdoc/dispatch-android-espresso/dispatch.android.espresso/-idling-dispatcher-provider-rule/-init-.md @@ -75,9 +75,7 @@ class IdlingCoroutineScopeRuleWithLifecycleSample { @Before fun setUp() { - LifecycleScopeFactory.set { - MainImmediateCoroutineScope(customDispatcherProvider) - } + LifecycleScopeFactory.set { customDispatcherProvider } ViewModelScopeFactory.set { MainImmediateCoroutineScope(customDispatcherProvider) } diff --git a/docs/kdoc/dispatch-android-espresso/dispatch.android.espresso/-idling-dispatcher-provider-rule/index.md b/docs/kdoc/dispatch-android-espresso/dispatch.android.espresso/-idling-dispatcher-provider-rule/index.md index 6c44779c3..e13c829a9 100644 --- a/docs/kdoc/dispatch-android-espresso/dispatch.android.espresso/-idling-dispatcher-provider-rule/index.md +++ b/docs/kdoc/dispatch-android-espresso/dispatch.android.espresso/-idling-dispatcher-provider-rule/index.md @@ -75,9 +75,7 @@ class IdlingCoroutineScopeRuleWithLifecycleSample { @Before fun setUp() { - LifecycleScopeFactory.set { - MainImmediateCoroutineScope(customDispatcherProvider) - } + LifecycleScopeFactory.set { customDispatcherProvider } ViewModelScopeFactory.set { MainImmediateCoroutineScope(customDispatcherProvider) } diff --git a/docs/kdoc/dispatch-android-lifecycle-extensions/dispatch.android.lifecycle/-lifecycle-scope-factory/index.md b/docs/kdoc/dispatch-android-lifecycle-extensions/dispatch.android.lifecycle/-lifecycle-scope-factory/index.md index d7325c705..20d2fc528 100644 --- a/docs/kdoc/dispatch-android-lifecycle-extensions/dispatch.android.lifecycle/-lifecycle-scope-factory/index.md +++ b/docs/kdoc/dispatch-android-lifecycle-extensions/dispatch.android.lifecycle/-lifecycle-scope-factory/index.md @@ -2,14 +2,17 @@ # LifecycleScopeFactory -`object LifecycleScopeFactory` [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle-extensions/src/main/java/dispatch/android/lifecycle/LifecycleScopeFactory.kt#L34) +`object LifecycleScopeFactory` [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle-extensions/src/main/java/dispatch/android/lifecycle/LifecycleScopeFactory.kt#L43) Factory holder for [LifecycleCoroutineScope](https://rbusarow.github.io/Dispatch/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/index.md)'s. -By default, `create` returns a [MainImmediateCoroutineScope](https://rbusarow.github.io/Dispatch/dispatch-core/dispatch.core/-main-immediate-coroutine-scope/index.md). +By default, `create` returns a [MainImmediateContext](https://rbusarow.github.io/Dispatch/dispatch-android-lifecycle/dispatch.android.lifecycle/-main-immediate-context.md). This factory can be overridden for testing or to include a custom [CoroutineContext](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin.coroutines/-coroutine-context/index.html) -in production code. This may be done in [Application.onCreate](https://developer.android.com/reference/android/app/Application.html#onCreate()) +in production code. This may be done in [Application.onCreate](https://developer.android.com/reference/android/app/Application.html#onCreate()), +or else as early as possible in the Application's existence. + +A custom factory will persist for the application's full lifecycle unless overwritten or [reset](https://rbusarow.github.io/Dispatch/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-scope-factory/reset.md). [reset](https://rbusarow.github.io/Dispatch/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-scope-factory/reset.md) may be used to reset the factory to default at any time. @@ -17,7 +20,8 @@ in production code. This may be done in [Application.onCreate](https://develope class MyApplication : Application { override fun onCreate() { - LifecycleScopeFactory.set { MainImmediateCoroutineScope() } + + LifecycleScopeFactory.set { MyCustomElement() + MainImmediateContext() } } } ``` @@ -27,14 +31,25 @@ class MyEspressoTest { @Before fun setUp() { - LifecycleScopeFactory.set { MainImmediateIdlingCoroutineScope() } + + val dispatcherProvider = IdlingDispatcherProvider() + + LifecycleScopeFactory.set { SupervisorJob() + dispatcherProvider + dispatcherProvider.mainImmediate } } } ``` +**See Also** + +[MainImmediateContext](https://rbusarow.github.io/Dispatch/dispatch-android-lifecycle/dispatch.android.lifecycle/-main-immediate-context.md) + +[LifecycleCoroutineScope](https://rbusarow.github.io/Dispatch/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/index.md) + +[LifecycleCoroutineScopeFactory](https://rbusarow.github.io/Dispatch/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope-factory/index.md) + ### Functions | Name | Summary | |---|---| | [reset](reset.md) | Immediately resets the factory function to its default.`fun reset(): `[`Unit`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin/-unit/index.html) | -| [set](set.md) | Override the default [MainImmediateCoroutineScope](https://rbusarow.github.io/Dispatch/dispatch-core/dispatch.core/-main-immediate-coroutine-scope/index.md) factory, for testing or to include a custom [CoroutineContext](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin.coroutines/-coroutine-context/index.html) in production code. This may be done in [Application.onCreate](https://developer.android.com/reference/android/app/Application.html#onCreate())`fun set(factory: () -> `[`MainImmediateCoroutineScope`](https://rbusarow.github.io/Dispatch/dispatch-core/dispatch.core/-main-immediate-coroutine-scope/index.md)`): `[`Unit`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin/-unit/index.html) | +| [set](set.md) | Override the default [MainImmediateCoroutineScope](https://rbusarow.github.io/Dispatch/dispatch-core/dispatch.core/-main-immediate-coroutine-scope/index.md) factory, for testing or to include a custom [CoroutineContext](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin.coroutines/-coroutine-context/index.html) in production code. This may be done in [Application.onCreate](https://developer.android.com/reference/android/app/Application.html#onCreate())`fun set(factory: `[`LifecycleCoroutineScopeFactory`](https://rbusarow.github.io/Dispatch/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope-factory/index.md)`): `[`Unit`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin/-unit/index.html)
`fun set(factory: () -> `[`CoroutineContext`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin.coroutines/-coroutine-context/index.html)`): `[`Unit`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin/-unit/index.html) | diff --git a/docs/kdoc/dispatch-android-lifecycle-extensions/dispatch.android.lifecycle/-lifecycle-scope-factory/reset.md b/docs/kdoc/dispatch-android-lifecycle-extensions/dispatch.android.lifecycle/-lifecycle-scope-factory/reset.md index 8d1834205..43772c2f1 100644 --- a/docs/kdoc/dispatch-android-lifecycle-extensions/dispatch.android.lifecycle/-lifecycle-scope-factory/reset.md +++ b/docs/kdoc/dispatch-android-lifecycle-extensions/dispatch.android.lifecycle/-lifecycle-scope-factory/reset.md @@ -2,7 +2,7 @@ # reset -`fun reset(): `[`Unit`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin/-unit/index.html) [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle-extensions/src/main/java/dispatch/android/lifecycle/LifecycleScopeFactory.kt#L58) +`fun reset(): `[`Unit`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin/-unit/index.html) [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle-extensions/src/main/java/dispatch/android/lifecycle/LifecycleScopeFactory.kt#L59) Immediately resets the factory function to its default. @@ -11,7 +11,10 @@ class MyEspressoTest { @Before fun setUp() { - LifecycleScopeFactory.set { MainImmediateIdlingCoroutineScope() } + + val dispatcherProvider = DefaultDispatcherProvider() + + LifecycleScopeFactory.set { SupervisorJob() + dispatcherProvider + dispatcherProvider.mainImmediate } } @After diff --git a/docs/kdoc/dispatch-android-lifecycle-extensions/dispatch.android.lifecycle/-lifecycle-scope-factory/set.md b/docs/kdoc/dispatch-android-lifecycle-extensions/dispatch.android.lifecycle/-lifecycle-scope-factory/set.md index 00131d2d1..9a9d59542 100644 --- a/docs/kdoc/dispatch-android-lifecycle-extensions/dispatch.android.lifecycle/-lifecycle-scope-factory/set.md +++ b/docs/kdoc/dispatch-android-lifecycle-extensions/dispatch.android.lifecycle/-lifecycle-scope-factory/set.md @@ -2,7 +2,8 @@ # set -`fun set(factory: () -> `[`MainImmediateCoroutineScope`](https://rbusarow.github.io/Dispatch/dispatch-core/dispatch.core/-main-immediate-coroutine-scope/index.md)`): `[`Unit`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin/-unit/index.html) [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle-extensions/src/main/java/dispatch/android/lifecycle/LifecycleScopeFactory.kt#L47) +`fun set(factory: `[`LifecycleCoroutineScopeFactory`](https://rbusarow.github.io/Dispatch/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope-factory/index.md)`): `[`Unit`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin/-unit/index.html) [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle-extensions/src/main/java/dispatch/android/lifecycle/LifecycleScopeFactory.kt#L78) +`fun set(factory: () -> `[`CoroutineContext`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin.coroutines/-coroutine-context/index.html)`): `[`Unit`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin/-unit/index.html) [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle-extensions/src/main/java/dispatch/android/lifecycle/LifecycleScopeFactory.kt#L97) Override the default [MainImmediateCoroutineScope](https://rbusarow.github.io/Dispatch/dispatch-core/dispatch.core/-main-immediate-coroutine-scope/index.md) factory, for testing or to include a custom [CoroutineContext](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin.coroutines/-coroutine-context/index.html) in production code. This may be done in [Application.onCreate](https://developer.android.com/reference/android/app/Application.html#onCreate()) @@ -11,7 +12,8 @@ in production code. This may be done in [Application.onCreate](https://develope class MyApplication : Application { override fun onCreate() { - LifecycleScopeFactory.set { MainImmediateCoroutineScope() } + + LifecycleScopeFactory.set { MyCustomElement() + MainImmediateContext() } } } ``` @@ -21,11 +23,15 @@ class MyEspressoTest { @Before fun setUp() { - LifecycleScopeFactory.set { MainImmediateIdlingCoroutineScope() } + + val dispatcherProvider = IdlingDispatcherProvider() + + LifecycleScopeFactory.set { SupervisorJob() + dispatcherProvider + dispatcherProvider.mainImmediate } } } ``` ### Parameters -`factory` - sets a custom [MainImmediateCoroutineScope](https://rbusarow.github.io/Dispatch/dispatch-core/dispatch.core/-main-immediate-coroutine-scope/index.md) factory to be used for all new instance creations until reset. \ No newline at end of file +`factory` - sets a custom [CoroutineContext](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin.coroutines/-coroutine-context/index.html) factory to be used for all new instance creations until reset. +Its [Elements](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin.coroutines/-coroutine-context/-element/index.html) will be re-used, except: \ No newline at end of file diff --git a/docs/kdoc/dispatch-android-lifecycle-extensions/dispatch.android.lifecycle/androidx.fragment.app.-fragment/index.md b/docs/kdoc/dispatch-android-lifecycle-extensions/dispatch.android.lifecycle/androidx.fragment.app.-fragment/index.md deleted file mode 100644 index f587a7d69..000000000 --- a/docs/kdoc/dispatch-android-lifecycle-extensions/dispatch.android.lifecycle/androidx.fragment.app.-fragment/index.md +++ /dev/null @@ -1,7 +0,0 @@ -[dispatch-android-lifecycle-extensions](../../index.md) / [dispatch.android.lifecycle](../index.md) / [androidx.fragment.app.Fragment](./index.md) - -### Extensions for androidx.fragment.app.Fragment - -| Name | Summary | -|---|---| -| [withViewLifecycleScope](with-view-lifecycle-scope.md) | [CoroutineScope](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html) helper for a [Fragment](https://developer.android.com/reference/androidx/androidx/fragment/app/Fragment.html)'s [ViewLifecycleOwner](https://developer.android.com/reference/androidx/androidx/fragment/app/FragmentViewLifecycleOwner.html).`fun `[`Fragment`](https://developer.android.com/reference/androidx/androidx/fragment/app/Fragment.html)`.withViewLifecycleScope(block: `[`ViewLifecycleCoroutineScope`](https://rbusarow.github.io/Dispatch/dispatch-android-lifecycle/dispatch.android.lifecycle/-view-lifecycle-coroutine-scope/index.md)`.() -> `[`Unit`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin/-unit/index.html)`): `[`Job`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-job/index.html) | diff --git a/docs/kdoc/dispatch-android-lifecycle-extensions/dispatch.android.lifecycle/androidx.fragment.app.-fragment/with-view-lifecycle-scope.md b/docs/kdoc/dispatch-android-lifecycle-extensions/dispatch.android.lifecycle/androidx.fragment.app.-fragment/with-view-lifecycle-scope.md deleted file mode 100644 index db2b311cb..000000000 --- a/docs/kdoc/dispatch-android-lifecycle-extensions/dispatch.android.lifecycle/androidx.fragment.app.-fragment/with-view-lifecycle-scope.md +++ /dev/null @@ -1,31 +0,0 @@ -[dispatch-android-lifecycle-extensions](../../index.md) / [dispatch.android.lifecycle](../index.md) / [androidx.fragment.app.Fragment](index.md) / [withViewLifecycleScope](./with-view-lifecycle-scope.md) - -# withViewLifecycleScope - -`@ExperimentalCoroutinesApi fun `[`Fragment`](https://developer.android.com/reference/androidx/androidx/fragment/app/Fragment.html)`.withViewLifecycleScope(block: `[`ViewLifecycleCoroutineScope`](https://rbusarow.github.io/Dispatch/dispatch-android-lifecycle/dispatch.android.lifecycle/-view-lifecycle-coroutine-scope/index.md)`.() -> `[`Unit`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin/-unit/index.html)`): `[`Job`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-job/index.html) [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle-extensions/src/main/java/dispatch/android/lifecycle/withViewLifecycleScope.kt#L30) - -[CoroutineScope](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html) helper for a [Fragment](https://developer.android.com/reference/androidx/androidx/fragment/app/Fragment.html)'s [ViewLifecycleOwner](https://developer.android.com/reference/androidx/androidx/fragment/app/FragmentViewLifecycleOwner.html). - -This function observes a `Fragment`'s [viewLifecycleOwnerLiveData](https://developer.android.com/reference/androidx/androidx/fragment/app/Fragment.html#getViewLifecycleOwnerLiveData()), -and invokes [block](https://rbusarow.github.io/Dispatch/dispatch-android-lifecycle/dispatch.android.lifecycle/with-view-lifecycle-scope/block.md). - -``` kotlin -class MyViewModel { - - val dataFlow = flow { - // ... - } -} - -class MyFragment : Fragment() { - - val myViewModel = MyViewModel() - - val observerJob = withViewLifecycleScope { - myViewModel.dataFlow.onEach { data -> - // ... - }.launchOnCreate() - } -} -``` - diff --git a/docs/kdoc/dispatch-android-lifecycle-extensions/index.md b/docs/kdoc/dispatch-android-lifecycle-extensions/index.md index 99611cb84..28e5a1cb9 100644 --- a/docs/kdoc/dispatch-android-lifecycle-extensions/index.md +++ b/docs/kdoc/dispatch-android-lifecycle-extensions/index.md @@ -48,7 +48,7 @@ class SomeApplication : Application() { override fun onCreate() { super.onCreate() // A custom factory can be set to add elements to the CoroutineContext - LifecycleScopeFactory.set { MainImmediateCoroutineScope() + SomeCustomElement() } + LifecycleScopeFactory.set { MainImmediateProvidedCoroutineContext() + SomeCustomElement() } } } ``` @@ -59,13 +59,13 @@ class SomeEspressoTest { fun setUp() { // This custom factory can be used to use custom scopes for testing, // such as an idling dispatcher - LifecycleScopeFactory.set { MainImmediateIdlingCoroutineScope() } + LifecycleScopeFactory.set { MainImmediateIdlingCoroutineScope().coroutineContext } } @After fun tearDown() { // The factory can also be reset to default - LifecycleScopeFactory.reset() + LifecycleCoroutineScopeFactory.reset() } } ``` @@ -90,7 +90,7 @@ class SomeFragmentEspressoTest { fun setUp() { // set a custom factory which is applied to all newly created lifecycleScopes LifecycleScopeFactory.set { - MainImmediateCoroutineScope() + idlingRule.dispatcherProvider + MainImmediateProvidedCoroutineContext() + idlingRule.dispatcherProvider } // now SomeFragment will use an IdlingDispatcher in its CoroutineScope diff --git a/docs/kdoc/dispatch-android-lifecycle/alltypes/index.md b/docs/kdoc/dispatch-android-lifecycle/alltypes/index.md index febfd574d..fe54c09c7 100644 --- a/docs/kdoc/dispatch-android-lifecycle/alltypes/index.md +++ b/docs/kdoc/dispatch-android-lifecycle/alltypes/index.md @@ -15,7 +15,15 @@ ##### [dispatch.android.lifecycle.LifecycleCoroutineScope](../dispatch.android.lifecycle/-lifecycle-coroutine-scope/index.md) -[MainImmediateCoroutineScope](https://rbusarow.github.io/Dispatch/dispatch-core/dispatch.core/-main-immediate-coroutine-scope/index.md) instance which is tied to a [Lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html). +[MainImmediateCoroutineScope](https://rbusarow.github.io/Dispatch/dispatch-core/dispatch.core/-main-immediate-coroutine-scope/index.md) which is tied to a [Lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html). + + +| + +##### [dispatch.android.lifecycle.LifecycleCoroutineScopeFactory](../dispatch.android.lifecycle/-lifecycle-coroutine-scope-factory/index.md) + +Factory for [LifecycleCoroutineScope](../dispatch.android.lifecycle/-lifecycle-coroutine-scope/index.md)s. This may be injected into a lifecycle-aware class +to provide custom [CoroutineContexts](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin.coroutines/-coroutine-context/index.html). | (extensions in package dispatch.android.lifecycle) diff --git a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope-factory/-init-.md b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope-factory/-init-.md new file mode 100644 index 000000000..58a9746cf --- /dev/null +++ b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope-factory/-init-.md @@ -0,0 +1,34 @@ +[dispatch-android-lifecycle](../../index.md) / [dispatch.android.lifecycle](../index.md) / [LifecycleCoroutineScopeFactory](index.md) / [<init>](./-init-.md) + +# <init> + +`LifecycleCoroutineScopeFactory(coroutineContextFactory: () -> `[`CoroutineContext`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin.coroutines/-coroutine-context/index.html)`)` + +Factory for [LifecycleCoroutineScope](../-lifecycle-coroutine-scope/index.md)s. This may be injected into a lifecycle-aware class +to provide custom [CoroutineContexts](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin.coroutines/-coroutine-context/index.html). + +``` kotlin +@Provides +fun provideFactory(): LifecycleCoroutineScopeFactory = + LifecycleCoroutineScopeFactory { + // other elements are added automatically + MyCustomElement() + } + +class MyFragment @Inject constructor( + factory: LifecycleCoroutineScopeFactory +) : Fragment() { + + val lifecycleScope = factory.create(lifecycle) + + init { + lifecycleScope.launchOnStart { + // ... + } + } +} +``` + +### Parameters + +`coroutineContextFactory` - the lambda defining the creating of a [CoroutineContext](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin.coroutines/-coroutine-context/index.html) \ No newline at end of file diff --git a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope-factory/create.md b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope-factory/create.md new file mode 100644 index 000000000..eaa1b14ee --- /dev/null +++ b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope-factory/create.md @@ -0,0 +1,11 @@ +[dispatch-android-lifecycle](../../index.md) / [dispatch.android.lifecycle](../index.md) / [LifecycleCoroutineScopeFactory](index.md) / [create](./create.md) + +# create + +`fun create(lifecycle: `[`Lifecycle`](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)`): `[`LifecycleCoroutineScope`](../-lifecycle-coroutine-scope/index.md) [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleCoroutineScopeFactory.kt#L37) + +Creates a new [LifecycleCoroutineScope](../-lifecycle-coroutine-scope/index.md) using `coroutineContextFactory` + +### Parameters + +`lifecycle` - the lifecycle which will be bound to the [LifecycleCoroutineScope](../-lifecycle-coroutine-scope/index.md) \ No newline at end of file diff --git a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope-factory/index.md b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope-factory/index.md new file mode 100644 index 000000000..acc0f6fdd --- /dev/null +++ b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope-factory/index.md @@ -0,0 +1,46 @@ +[dispatch-android-lifecycle](../../index.md) / [dispatch.android.lifecycle](../index.md) / [LifecycleCoroutineScopeFactory](./index.md) + +# LifecycleCoroutineScopeFactory + +`class LifecycleCoroutineScopeFactory` [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleCoroutineScopeFactory.kt#L28) + +Factory for [LifecycleCoroutineScope](../-lifecycle-coroutine-scope/index.md)s. This may be injected into a lifecycle-aware class +to provide custom [CoroutineContexts](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin.coroutines/-coroutine-context/index.html). + +``` kotlin +@Provides +fun provideFactory(): LifecycleCoroutineScopeFactory = + LifecycleCoroutineScopeFactory { + // other elements are added automatically + MyCustomElement() + } + +class MyFragment @Inject constructor( + factory: LifecycleCoroutineScopeFactory +) : Fragment() { + + val lifecycleScope = factory.create(lifecycle) + + init { + lifecycleScope.launchOnStart { + // ... + } + } +} +``` + +### Parameters + +`coroutineContextFactory` - the lambda defining the creating of a [CoroutineContext](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin.coroutines/-coroutine-context/index.html) + +### Constructors + +| Name | Summary | +|---|---| +| [<init>](-init-.md) | Factory for [LifecycleCoroutineScope](../-lifecycle-coroutine-scope/index.md)s. This may be injected into a lifecycle-aware class to provide custom [CoroutineContexts](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin.coroutines/-coroutine-context/index.html).`LifecycleCoroutineScopeFactory(coroutineContextFactory: () -> `[`CoroutineContext`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin.coroutines/-coroutine-context/index.html)`)` | + +### Functions + +| Name | Summary | +|---|---| +| [create](create.md) | Creates a new [LifecycleCoroutineScope](../-lifecycle-coroutine-scope/index.md) using `coroutineContextFactory``fun create(lifecycle: `[`Lifecycle`](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)`): `[`LifecycleCoroutineScope`](../-lifecycle-coroutine-scope/index.md) | diff --git a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/-init-.md b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/-init-.md index 9553837ce..a6744126e 100644 --- a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/-init-.md +++ b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/-init-.md @@ -2,17 +2,17 @@ # <init> -`LifecycleCoroutineScope(lifecycle: `[`Lifecycle`](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)`, coroutineScope: `[`MainImmediateCoroutineScope`](https://rbusarow.github.io/Dispatch/dispatch-core/dispatch.core/-main-immediate-coroutine-scope/index.md)`)` +`LifecycleCoroutineScope(lifecycle: `[`Lifecycle`](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)`, coroutineContext: `[`CoroutineContext`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin.coroutines/-coroutine-context/index.html)` = MainImmediateContext())` -[MainImmediateCoroutineScope](https://rbusarow.github.io/Dispatch/dispatch-core/dispatch.core/-main-immediate-coroutine-scope/index.md) instance which is tied to a [Lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html). +[MainImmediateCoroutineScope](https://rbusarow.github.io/Dispatch/dispatch-core/dispatch.core/-main-immediate-coroutine-scope/index.md) which is tied to a [Lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html). The [CoroutineScope](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html) provides lifecycle-aware [launch](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/launch.html) functions which will automatically start upon reaching their associated [Lifecycle.Event](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/Event.html), -then automatically cancel upon the [lifecycle](lifecycle.md) dropping below that state. Reaching +then automatically cancel upon the lifecycle dropping below that state. Reaching that state again will start a new [Job](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-job/index.html). -If this `CoroutineScope` has a [Job](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-job/index.html), it will be cancelled automatically -as soon as the [lifecycle](lifecycle.md) reaches [DESTROYED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#DESTROYED). +This `CoroutineScope`'s [Job](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-job/index.html) will be cancelled automatically +as soon as the `lifecycle` reaches [DESTROYED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#DESTROYED). ``` kotlin runBlocking { @@ -20,18 +20,52 @@ runBlocking { // This could be any LifecycleOwner -- Fragments, Activities, Services... class SomeFragment : Fragment() { - init { + val lifecycleScope = LifecycleCoroutineScope(lifecycle) - // auto-created MainImmediateCoroutineScope which is lifecycle-aware - lifecycleScope //... + init { // active only when "resumed". starts a fresh coroutine each time + lifecycleScope.launchOnResume { } + + // active only when "started". starts a fresh coroutine each time // this is a rough proxy for LiveData behavior + lifecycleScope.launchOnStart { } + + // active after only the first "started" event, and never re-started + lifecycleScope.launchOnStart(minimumStatePolicy = CANCEL) { } + + // launch when created, automatically stop on destroy + lifecycleScope.launchOnCreate { } + + // it works as a normal CoroutineScope as well (because it is) + lifecycleScope.launchMain { } + } + } + } +``` + +``` kotlin +runBlocking { + + // This could be any LifecycleOwner -- Fragments, Activities, Services... + class SomeFragment : Fragment() { + + val context = Job() + DispatcherProvider() + + val lifecycleScope = LifecycleCoroutineScope(lifecycle, context) + + init { + + // active only when "resumed". starts a fresh coroutine each time lifecycleScope.launchOnResume { } // active only when "started". starts a fresh coroutine each time + // this is a rough proxy for LiveData behavior lifecycleScope.launchOnStart { } + // active after only the first "started" event, and never re-started + lifecycleScope.launchOnStart(minimumStatePolicy = CANCEL) { } + // launch when created, automatically stop on destroy lifecycleScope.launchOnCreate { } @@ -45,4 +79,7 @@ runBlocking { ### Parameters -`lifecycle` - the lifecycle to which this [MainImmediateCoroutineScope](https://rbusarow.github.io/Dispatch/dispatch-core/dispatch.core/-main-immediate-coroutine-scope/index.md) is linked. \ No newline at end of file +`lifecycle` - the lifecycle to which this [MainImmediateCoroutineScope](https://rbusarow.github.io/Dispatch/dispatch-core/dispatch.core/-main-immediate-coroutine-scope/index.md) is linked. + +`coroutineContext` - the source CoroutineContext which will be converted to a [MainImmediateCoroutineScope](https://rbusarow.github.io/Dispatch/dispatch-core/dispatch.core/-main-immediate-coroutine-scope/index.md). +Its [Elements](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin.coroutines/-coroutine-context/-element/index.html) will be re-used, except: \ No newline at end of file diff --git a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/-minimum-state-policy/-c-a-n-c-e-l.md b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/-minimum-state-policy/-c-a-n-c-e-l.md index fb84b15c0..0cd007349 100644 --- a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/-minimum-state-policy/-c-a-n-c-e-l.md +++ b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/-minimum-state-policy/-c-a-n-c-e-l.md @@ -2,7 +2,7 @@ # CANCEL -`CANCEL` [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleCoroutineScope.kt#L124) +`CANCEL` [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleCoroutineScope.kt#L141) When using `CANCEL`, a coroutine will be created the first time the [lifecycle](../lifecycle.md) meets the minimum state, and cancelled upon dropping below it. diff --git a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/-minimum-state-policy/-r-e-s-t-a-r-t_-e-v-e-r-y.md b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/-minimum-state-policy/-r-e-s-t-a-r-t_-e-v-e-r-y.md index c121e9425..9fe0900dc 100644 --- a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/-minimum-state-policy/-r-e-s-t-a-r-t_-e-v-e-r-y.md +++ b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/-minimum-state-policy/-r-e-s-t-a-r-t_-e-v-e-r-y.md @@ -2,7 +2,7 @@ # RESTART_EVERY -`RESTART_EVERY` [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleCoroutineScope.kt#L137) +`RESTART_EVERY` [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleCoroutineScope.kt#L154) When using `RESTART_EVERY`, a coroutine will be created every time the [lifecycle](../lifecycle.md) meets the minimum state, and will be cancelled upon dropping below it. diff --git a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/-minimum-state-policy/index.md b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/-minimum-state-policy/index.md index 33878daad..65aaccb12 100644 --- a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/-minimum-state-policy/index.md +++ b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/-minimum-state-policy/index.md @@ -2,7 +2,7 @@ # MinimumStatePolicy -`enum class MinimumStatePolicy` [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleCoroutineScope.kt#L114) +`enum class MinimumStatePolicy` [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleCoroutineScope.kt#L131) Describes the way a particular [Job](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-job/index.html) will behave if the [lifecycle](../lifecycle.md) passes below the minimum state before said [Job](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-job/index.html) has completed. diff --git a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/index.md b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/index.md index 8ba3572ce..521c29845 100644 --- a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/index.md +++ b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/index.md @@ -2,17 +2,17 @@ # LifecycleCoroutineScope -`class LifecycleCoroutineScope : `[`MainImmediateCoroutineScope`](https://rbusarow.github.io/Dispatch/dispatch-core/dispatch.core/-main-immediate-coroutine-scope/index.md) [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleCoroutineScope.kt#L38) +`open class LifecycleCoroutineScope : `[`MainImmediateCoroutineScope`](https://rbusarow.github.io/Dispatch/dispatch-core/dispatch.core/-main-immediate-coroutine-scope/index.md) [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleCoroutineScope.kt#L55) -[MainImmediateCoroutineScope](https://rbusarow.github.io/Dispatch/dispatch-core/dispatch.core/-main-immediate-coroutine-scope/index.md) instance which is tied to a [Lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html). +[MainImmediateCoroutineScope](https://rbusarow.github.io/Dispatch/dispatch-core/dispatch.core/-main-immediate-coroutine-scope/index.md) which is tied to a [Lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html). The [CoroutineScope](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html) provides lifecycle-aware [launch](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/launch.html) functions which will automatically start upon reaching their associated [Lifecycle.Event](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/Event.html), -then automatically cancel upon the [lifecycle](lifecycle.md) dropping below that state. Reaching +then automatically cancel upon the lifecycle dropping below that state. Reaching that state again will start a new [Job](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-job/index.html). -If this `CoroutineScope` has a [Job](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-job/index.html), it will be cancelled automatically -as soon as the [lifecycle](lifecycle.md) reaches [DESTROYED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#DESTROYED). +This `CoroutineScope`'s [Job](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-job/index.html) will be cancelled automatically +as soon as the `lifecycle` reaches [DESTROYED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#DESTROYED). ``` kotlin runBlocking { @@ -20,18 +20,52 @@ runBlocking { // This could be any LifecycleOwner -- Fragments, Activities, Services... class SomeFragment : Fragment() { - init { + val lifecycleScope = LifecycleCoroutineScope(lifecycle) - // auto-created MainImmediateCoroutineScope which is lifecycle-aware - lifecycleScope //... + init { // active only when "resumed". starts a fresh coroutine each time + lifecycleScope.launchOnResume { } + + // active only when "started". starts a fresh coroutine each time // this is a rough proxy for LiveData behavior + lifecycleScope.launchOnStart { } + + // active after only the first "started" event, and never re-started + lifecycleScope.launchOnStart(minimumStatePolicy = CANCEL) { } + + // launch when created, automatically stop on destroy + lifecycleScope.launchOnCreate { } + + // it works as a normal CoroutineScope as well (because it is) + lifecycleScope.launchMain { } + } + } + } +``` + +``` kotlin +runBlocking { + + // This could be any LifecycleOwner -- Fragments, Activities, Services... + class SomeFragment : Fragment() { + + val context = Job() + DispatcherProvider() + + val lifecycleScope = LifecycleCoroutineScope(lifecycle, context) + + init { + + // active only when "resumed". starts a fresh coroutine each time lifecycleScope.launchOnResume { } // active only when "started". starts a fresh coroutine each time + // this is a rough proxy for LiveData behavior lifecycleScope.launchOnStart { } + // active after only the first "started" event, and never re-started + lifecycleScope.launchOnStart(minimumStatePolicy = CANCEL) { } + // launch when created, automatically stop on destroy lifecycleScope.launchOnCreate { } @@ -47,6 +81,9 @@ runBlocking { `lifecycle` - the lifecycle to which this [MainImmediateCoroutineScope](https://rbusarow.github.io/Dispatch/dispatch-core/dispatch.core/-main-immediate-coroutine-scope/index.md) is linked. +`coroutineContext` - the source CoroutineContext which will be converted to a [MainImmediateCoroutineScope](https://rbusarow.github.io/Dispatch/dispatch-core/dispatch.core/-main-immediate-coroutine-scope/index.md). +Its [Elements](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin.coroutines/-coroutine-context/-element/index.html) will be re-used, except: + ### Types | Name | Summary | @@ -57,7 +94,7 @@ runBlocking { | Name | Summary | |---|---| -| [<init>](-init-.md) | [MainImmediateCoroutineScope](https://rbusarow.github.io/Dispatch/dispatch-core/dispatch.core/-main-immediate-coroutine-scope/index.md) instance which is tied to a [Lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html).`LifecycleCoroutineScope(lifecycle: `[`Lifecycle`](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)`, coroutineScope: `[`MainImmediateCoroutineScope`](https://rbusarow.github.io/Dispatch/dispatch-core/dispatch.core/-main-immediate-coroutine-scope/index.md)`)` | +| [<init>](-init-.md) | [MainImmediateCoroutineScope](https://rbusarow.github.io/Dispatch/dispatch-core/dispatch.core/-main-immediate-coroutine-scope/index.md) which is tied to a [Lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html).`LifecycleCoroutineScope(lifecycle: `[`Lifecycle`](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)`, coroutineContext: `[`CoroutineContext`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin.coroutines/-coroutine-context/index.html)` = MainImmediateContext())` | ### Properties @@ -72,3 +109,9 @@ runBlocking { | [launchOnCreate](launch-on-create.md) | Lifecycle-aware function for launching a coroutine any time the [Lifecycle.State](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html) is at least [Lifecycle.State.CREATED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#CREATED).`fun launchOnCreate(minimumStatePolicy: MinimumStatePolicy = MinimumStatePolicy.RESTART_EVERY, block: suspend `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`.() -> `[`Unit`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin/-unit/index.html)`): `[`Job`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-job/index.html) | | [launchOnResume](launch-on-resume.md) | Lifecycle-aware function for launching a coroutine any time the [Lifecycle.State](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html) is at least [Lifecycle.State.RESUMED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#RESUMED).`fun launchOnResume(minimumStatePolicy: MinimumStatePolicy = MinimumStatePolicy.RESTART_EVERY, block: suspend `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`.() -> `[`Unit`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin/-unit/index.html)`): `[`Job`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-job/index.html) | | [launchOnStart](launch-on-start.md) | Lifecycle-aware function for launching a coroutine any time the [Lifecycle.State](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html) is at least [Lifecycle.State.STARTED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#STARTED).`fun launchOnStart(minimumStatePolicy: MinimumStatePolicy = MinimumStatePolicy.RESTART_EVERY, block: suspend `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`.() -> `[`Unit`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin/-unit/index.html)`): `[`Job`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-job/index.html) | + +### Companion Object Functions + +| Name | Summary | +|---|---| +| [invoke](invoke.md) | [MainImmediateCoroutineScope](https://rbusarow.github.io/Dispatch/dispatch-core/dispatch.core/-main-immediate-coroutine-scope/index.md) which is tied to a [Lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html).`operator fun invoke(lifecycle: `[`Lifecycle`](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)`, coroutineScope: `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`): `[`LifecycleCoroutineScope`](./index.md) | diff --git a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/invoke.md b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/invoke.md new file mode 100644 index 000000000..99dff60b2 --- /dev/null +++ b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/invoke.md @@ -0,0 +1,55 @@ +[dispatch-android-lifecycle](../../index.md) / [dispatch.android.lifecycle](../index.md) / [LifecycleCoroutineScope](index.md) / [invoke](./invoke.md) + +# invoke + +`operator fun invoke(lifecycle: `[`Lifecycle`](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)`, coroutineScope: `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`): `[`LifecycleCoroutineScope`](index.md) [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleCoroutineScope.kt#L178) + +[MainImmediateCoroutineScope](https://rbusarow.github.io/Dispatch/dispatch-core/dispatch.core/-main-immediate-coroutine-scope/index.md) which is tied to a [Lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html). + +The [CoroutineScope](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html) provides lifecycle-aware [launch](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/launch.html) functions +which will automatically start upon reaching their associated [Lifecycle.Event](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/Event.html), +then automatically cancel upon the lifecycle dropping below that state. Reaching +that state again will start a new [Job](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-job/index.html). + +If this `CoroutineScope` has a [Job](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-job/index.html), it will be cancelled automatically +as soon as the `lifecycle` reaches [DESTROYED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#DESTROYED). + +``` kotlin +runBlocking { + + // This could be any LifecycleOwner -- Fragments, Activities, Services... + class SomeFragment @Inject constructor( + coroutineScope: CoroutineScope // could be any type of CoroutineScope + ) : Fragment() { + + val lifecycleScope = LifecycleCoroutineScope(lifecycle, coroutineScope) + + init { + + // active only when "resumed". starts a fresh coroutine each time + lifecycleScope.launchOnResume { } + + // active only when "started". starts a fresh coroutine each time + // this is a rough proxy for LiveData behavior + lifecycleScope.launchOnStart { } + + // active after only the first "started" event, and never re-started + lifecycleScope.launchOnStart(minimumStatePolicy = CANCEL) { } + + // launch when created, automatically stop on destroy + lifecycleScope.launchOnCreate { } + + // it works as a normal CoroutineScope as well (because it is) + lifecycleScope.launchMain { } + + } + } + } +``` + +### Parameters + +`lifecycle` - the lifecycle to which this [MainImmediateCoroutineScope](https://rbusarow.github.io/Dispatch/dispatch-core/dispatch.core/-main-immediate-coroutine-scope/index.md) is linked. + +`coroutineScope` - the source CoroutineScope which will be converted to a [MainImmediateCoroutineScope](https://rbusarow.github.io/Dispatch/dispatch-core/dispatch.core/-main-immediate-coroutine-scope/index.md). +Its [CoroutineContext](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin.coroutines/-coroutine-context/index.html) will be re-used, except: \ No newline at end of file diff --git a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/launch-on-create.md b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/launch-on-create.md index ba1e75ded..723138ffe 100644 --- a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/launch-on-create.md +++ b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/launch-on-create.md @@ -2,15 +2,15 @@ # launchOnCreate -`fun launchOnCreate(minimumStatePolicy: MinimumStatePolicy = MinimumStatePolicy.RESTART_EVERY, block: suspend `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`.() -> `[`Unit`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin/-unit/index.html)`): `[`Job`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-job/index.html) [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleCoroutineScope.kt#L65) +`fun launchOnCreate(minimumStatePolicy: MinimumStatePolicy = MinimumStatePolicy.RESTART_EVERY, block: suspend `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`.() -> `[`Unit`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin/-unit/index.html)`): `[`Job`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-job/index.html) [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleCoroutineScope.kt#L82) Lifecycle-aware function for launching a coroutine any time the [Lifecycle.State](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html) is at least [Lifecycle.State.CREATED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#CREATED). -[block](launch-on-create.md#dispatch.android.lifecycle.LifecycleCoroutineScope$launchOnCreate(dispatch.android.lifecycle.LifecycleCoroutineScope.MinimumStatePolicy, kotlin.coroutines.SuspendFunction1((kotlinx.coroutines.CoroutineScope, kotlin.Unit)))/block) is executed using the receiver [CoroutineScope](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)'s [Job](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-job/index.html) as a parent, +`block` is executed using the receiver [CoroutineScope](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)'s [Job](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-job/index.html) as a parent, but always executes using [Dispatchers.Main](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-dispatchers/-main.html) as its [CoroutineDispatcher](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-dispatcher/index.html). -Execution of [block](launch-on-create.md#dispatch.android.lifecycle.LifecycleCoroutineScope$launchOnCreate(dispatch.android.lifecycle.LifecycleCoroutineScope.MinimumStatePolicy, kotlin.coroutines.SuspendFunction1((kotlinx.coroutines.CoroutineScope, kotlin.Unit)))/block) is cancelled when the receiver [CoroutineScope](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html) is cancelled, +Execution of `block` is cancelled when the receiver [CoroutineScope](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html) is cancelled, or when [lifecycle](lifecycle.md)'s [Lifecycle.State](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html) drops below [Lifecycle.State.CREATED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#CREATED). ``` kotlin diff --git a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/launch-on-resume.md b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/launch-on-resume.md index c2eaaf680..aa169b095 100644 --- a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/launch-on-resume.md +++ b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/launch-on-resume.md @@ -2,15 +2,15 @@ # launchOnResume -`fun launchOnResume(minimumStatePolicy: MinimumStatePolicy = MinimumStatePolicy.RESTART_EVERY, block: suspend `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`.() -> `[`Unit`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin/-unit/index.html)`): `[`Job`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-job/index.html) [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleCoroutineScope.kt#L105) +`fun launchOnResume(minimumStatePolicy: MinimumStatePolicy = MinimumStatePolicy.RESTART_EVERY, block: suspend `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`.() -> `[`Unit`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin/-unit/index.html)`): `[`Job`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-job/index.html) [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleCoroutineScope.kt#L122) Lifecycle-aware function for launching a coroutine any time the [Lifecycle.State](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html) is at least [Lifecycle.State.RESUMED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#RESUMED). -[block](launch-on-resume.md#dispatch.android.lifecycle.LifecycleCoroutineScope$launchOnResume(dispatch.android.lifecycle.LifecycleCoroutineScope.MinimumStatePolicy, kotlin.coroutines.SuspendFunction1((kotlinx.coroutines.CoroutineScope, kotlin.Unit)))/block) is executed using the receiver [CoroutineScope](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)'s [Job](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-job/index.html) as a parent, +`block` is executed using the receiver [CoroutineScope](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)'s [Job](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-job/index.html) as a parent, but always executes using [Dispatchers.Main](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-dispatchers/-main.html) as its [CoroutineDispatcher](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-dispatcher/index.html). -Execution of [block](launch-on-resume.md#dispatch.android.lifecycle.LifecycleCoroutineScope$launchOnResume(dispatch.android.lifecycle.LifecycleCoroutineScope.MinimumStatePolicy, kotlin.coroutines.SuspendFunction1((kotlinx.coroutines.CoroutineScope, kotlin.Unit)))/block) is cancelled when the receiver [CoroutineScope](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html) is cancelled, +Execution of `block` is cancelled when the receiver [CoroutineScope](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html) is cancelled, or when [lifecycle](lifecycle.md)'s [Lifecycle.State](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html) drops below [Lifecycle.State.RESUMED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#RESUMED). ``` kotlin diff --git a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/launch-on-start.md b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/launch-on-start.md index 796260208..7f2bb3f96 100644 --- a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/launch-on-start.md +++ b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/launch-on-start.md @@ -2,15 +2,15 @@ # launchOnStart -`fun launchOnStart(minimumStatePolicy: MinimumStatePolicy = MinimumStatePolicy.RESTART_EVERY, block: suspend `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`.() -> `[`Unit`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin/-unit/index.html)`): `[`Job`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-job/index.html) [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleCoroutineScope.kt#L85) +`fun launchOnStart(minimumStatePolicy: MinimumStatePolicy = MinimumStatePolicy.RESTART_EVERY, block: suspend `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`.() -> `[`Unit`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin/-unit/index.html)`): `[`Job`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-job/index.html) [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleCoroutineScope.kt#L102) Lifecycle-aware function for launching a coroutine any time the [Lifecycle.State](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html) is at least [Lifecycle.State.STARTED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#STARTED). -[block](launch-on-start.md#dispatch.android.lifecycle.LifecycleCoroutineScope$launchOnStart(dispatch.android.lifecycle.LifecycleCoroutineScope.MinimumStatePolicy, kotlin.coroutines.SuspendFunction1((kotlinx.coroutines.CoroutineScope, kotlin.Unit)))/block) is executed using the receiver [CoroutineScope](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)'s [Job](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-job/index.html) as a parent, +`block` is executed using the receiver [CoroutineScope](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)'s [Job](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-job/index.html) as a parent, but always executes using [Dispatchers.Main](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-dispatchers/-main.html) as its [CoroutineDispatcher](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-dispatcher/index.html). -Execution of [block](launch-on-start.md#dispatch.android.lifecycle.LifecycleCoroutineScope$launchOnStart(dispatch.android.lifecycle.LifecycleCoroutineScope.MinimumStatePolicy, kotlin.coroutines.SuspendFunction1((kotlinx.coroutines.CoroutineScope, kotlin.Unit)))/block) is cancelled when the receiver [CoroutineScope](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html) is cancelled, +Execution of `block` is cancelled when the receiver [CoroutineScope](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html) is cancelled, or when [lifecycle](lifecycle.md)'s [Lifecycle.State](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html) drops below [Lifecycle.State.STARTED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#STARTED). ``` kotlin diff --git a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/lifecycle.md b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/lifecycle.md index 2958501ee..1bd8993c0 100644 --- a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/lifecycle.md +++ b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-lifecycle-coroutine-scope/lifecycle.md @@ -2,7 +2,7 @@ # lifecycle -`val lifecycle: `[`Lifecycle`](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html) [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleCoroutineScope.kt#L39) +`val lifecycle: `[`Lifecycle`](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html) [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleCoroutineScope.kt#L56) the lifecycle to which this [MainImmediateCoroutineScope](https://rbusarow.github.io/Dispatch/dispatch-core/dispatch.core/-main-immediate-coroutine-scope/index.md) is linked. diff --git a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-main-immediate-context.md b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-main-immediate-context.md new file mode 100644 index 000000000..9f2213da5 --- /dev/null +++ b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-main-immediate-context.md @@ -0,0 +1,12 @@ +[dispatch-android-lifecycle](../index.md) / [dispatch.android.lifecycle](index.md) / [MainImmediateContext](./-main-immediate-context.md) + +# MainImmediateContext + +`fun MainImmediateContext(): `[`CoroutineContext`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin.coroutines/-coroutine-context/index.html) [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleCoroutineScope.kt#L29) + +Default implementation of a [CoroutineContext](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin.coroutines/-coroutine-context/index.html) as seen in a `MainImmediateCoroutineScope`. + +**See Also** + +[MainImmediateCoroutineScope](https://rbusarow.github.io/Dispatch/dispatch-core/dispatch.core/-main-immediate-coroutine-scope/index.md) + diff --git a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-view-lifecycle-coroutine-scope/index.md b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-view-lifecycle-coroutine-scope/index.md deleted file mode 100644 index 206ec6630..000000000 --- a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-view-lifecycle-coroutine-scope/index.md +++ /dev/null @@ -1,15 +0,0 @@ -[dispatch-android-lifecycle](../../index.md) / [dispatch.android.lifecycle](../index.md) / [ViewLifecycleCoroutineScope](./index.md) - -# ViewLifecycleCoroutineScope - -`class ViewLifecycleCoroutineScope : `[`LifecycleCoroutineScope`](../-lifecycle-coroutine-scope/index.md) [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/ViewLifecycleCoroutineScope.kt#L28) - -[LifecycleCoroutineScope](../-lifecycle-coroutine-scope/index.md) instance which is tied to a [Fragment's](https://developer.android.com/reference/androidx/androidx/fragment/app/Fragment.html) View [lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html). - -### Functions - -| Name | Summary | -|---|---| -| [launchOnCreate](launch-on-create.md) | Every time the View [Lifecycle State](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html) reaches [CREATED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#CREATED), create a new coroutine and collect this [Flow](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines.flow/-flow/index.html).`fun `[`Flow`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines.flow/-flow/index.html)`.launchOnCreate(): `[`Job`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-job/index.html) | -| [launchOnResume](launch-on-resume.md) | Every time the View [Lifecycle State](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html) reaches [RESUMED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#RESUMED), create a new coroutine and collect this [Flow](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines.flow/-flow/index.html).`fun `[`Flow`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines.flow/-flow/index.html)`.launchOnResume(): `[`Job`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-job/index.html) | -| [launchOnStart](launch-on-start.md) | Every time the View [Lifecycle State](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html) reaches [STARTED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#STARTED), create a new coroutine and collect this [Flow](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines.flow/-flow/index.html).`fun `[`Flow`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines.flow/-flow/index.html)`.launchOnStart(): `[`Job`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-job/index.html) | diff --git a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-view-lifecycle-coroutine-scope/launch-on-create.md b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-view-lifecycle-coroutine-scope/launch-on-create.md deleted file mode 100644 index 64cd1395a..000000000 --- a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-view-lifecycle-coroutine-scope/launch-on-create.md +++ /dev/null @@ -1,12 +0,0 @@ -[dispatch-android-lifecycle](../../index.md) / [dispatch.android.lifecycle](../index.md) / [ViewLifecycleCoroutineScope](index.md) / [launchOnCreate](./launch-on-create.md) - -# launchOnCreate - -`fun `[`Flow`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines.flow/-flow/index.html)`.launchOnCreate(): `[`Job`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-job/index.html) [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/ViewLifecycleCoroutineScope.kt#L38) - -Every time the View [Lifecycle State](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html) reaches [CREATED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#CREATED), create a new coroutine and collect this [Flow](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines.flow/-flow/index.html). - -**See Also** - -[kotlinx.coroutines.flow.launchIn](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines.flow/launch-in.html) - diff --git a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-view-lifecycle-coroutine-scope/launch-on-resume.md b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-view-lifecycle-coroutine-scope/launch-on-resume.md deleted file mode 100644 index 8b0582414..000000000 --- a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-view-lifecycle-coroutine-scope/launch-on-resume.md +++ /dev/null @@ -1,12 +0,0 @@ -[dispatch-android-lifecycle](../../index.md) / [dispatch.android.lifecycle](../index.md) / [ViewLifecycleCoroutineScope](index.md) / [launchOnResume](./launch-on-resume.md) - -# launchOnResume - -`fun `[`Flow`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines.flow/-flow/index.html)`.launchOnResume(): `[`Job`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-job/index.html) [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/ViewLifecycleCoroutineScope.kt#L52) - -Every time the View [Lifecycle State](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html) reaches [RESUMED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#RESUMED), create a new coroutine and collect this [Flow](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines.flow/-flow/index.html). - -**See Also** - -[kotlinx.coroutines.flow.launchIn](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines.flow/launch-in.html) - diff --git a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-view-lifecycle-coroutine-scope/launch-on-start.md b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-view-lifecycle-coroutine-scope/launch-on-start.md deleted file mode 100644 index a806c0dc6..000000000 --- a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/-view-lifecycle-coroutine-scope/launch-on-start.md +++ /dev/null @@ -1,12 +0,0 @@ -[dispatch-android-lifecycle](../../index.md) / [dispatch.android.lifecycle](../index.md) / [ViewLifecycleCoroutineScope](index.md) / [launchOnStart](./launch-on-start.md) - -# launchOnStart - -`fun `[`Flow`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines.flow/-flow/index.html)`.launchOnStart(): `[`Job`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-job/index.html) [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/ViewLifecycleCoroutineScope.kt#L45) - -Every time the View [Lifecycle State](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html) reaches [STARTED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#STARTED), create a new coroutine and collect this [Flow](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines.flow/-flow/index.html). - -**See Also** - -[kotlinx.coroutines.flow.launchIn](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines.flow/launch-in.html) - diff --git a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/androidx.lifecycle.-lifecycle-owner/index.md b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/androidx.lifecycle.-lifecycle-owner/index.md index 51b1109a8..73c75835d 100644 --- a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/androidx.lifecycle.-lifecycle-owner/index.md +++ b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/androidx.lifecycle.-lifecycle-owner/index.md @@ -4,6 +4,6 @@ | Name | Summary | |---|---| -| [onNextCreate](on-next-create.md) | Executes [block](on-next-create.md#dispatch.android.lifecycle$onNextCreate(androidx.lifecycle.LifecycleOwner, kotlin.coroutines.SuspendFunction1((kotlinx.coroutines.CoroutineScope, dispatch.android.lifecycle.onNextCreate.T)))/block) one time, the next time the [Lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)'s state is at least [Lifecycle.State.CREATED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#CREATED).`suspend fun `[`LifecycleOwner`](https://developer.android.com/reference/androidx/androidx/lifecycle/LifecycleOwner.html)`.onNextCreate(block: suspend `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`.() -> T): T?` | -| [onNextResume](on-next-resume.md) | Executes [block](on-next-resume.md#dispatch.android.lifecycle$onNextResume(androidx.lifecycle.LifecycleOwner, kotlin.coroutines.SuspendFunction1((kotlinx.coroutines.CoroutineScope, dispatch.android.lifecycle.onNextResume.T)))/block) one time, the next time the [Lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)'s state is at least [Lifecycle.State.RESUMED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#RESUMED).`suspend fun `[`LifecycleOwner`](https://developer.android.com/reference/androidx/androidx/lifecycle/LifecycleOwner.html)`.onNextResume(block: suspend `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`.() -> T): T?` | -| [onNextStart](on-next-start.md) | Executes [block](on-next-start.md#dispatch.android.lifecycle$onNextStart(androidx.lifecycle.LifecycleOwner, kotlin.coroutines.SuspendFunction1((kotlinx.coroutines.CoroutineScope, dispatch.android.lifecycle.onNextStart.T)))/block) one time, the next time the [Lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)'s state is at least [Lifecycle.State.STARTED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#STARTED).`suspend fun `[`LifecycleOwner`](https://developer.android.com/reference/androidx/androidx/lifecycle/LifecycleOwner.html)`.onNextStart(block: suspend `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`.() -> T): T?` | +| [onNextCreate](on-next-create.md) | Executes `block` one time, the next time the [Lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)'s state is at least [Lifecycle.State.CREATED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#CREATED).`suspend fun `[`LifecycleOwner`](https://developer.android.com/reference/androidx/androidx/lifecycle/LifecycleOwner.html)`.onNextCreate(block: suspend `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`.() -> T): T?` | +| [onNextResume](on-next-resume.md) | Executes `block` one time, the next time the [Lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)'s state is at least [Lifecycle.State.RESUMED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#RESUMED).`suspend fun `[`LifecycleOwner`](https://developer.android.com/reference/androidx/androidx/lifecycle/LifecycleOwner.html)`.onNextResume(block: suspend `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`.() -> T): T?` | +| [onNextStart](on-next-start.md) | Executes `block` one time, the next time the [Lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)'s state is at least [Lifecycle.State.STARTED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#STARTED).`suspend fun `[`LifecycleOwner`](https://developer.android.com/reference/androidx/androidx/lifecycle/LifecycleOwner.html)`.onNextStart(block: suspend `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`.() -> T): T?` | diff --git a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/androidx.lifecycle.-lifecycle-owner/on-next-create.md b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/androidx.lifecycle.-lifecycle-owner/on-next-create.md index e5ef9fad5..8283c7410 100644 --- a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/androidx.lifecycle.-lifecycle-owner/on-next-create.md +++ b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/androidx.lifecycle.-lifecycle-owner/on-next-create.md @@ -2,11 +2,11 @@ # onNextCreate -`suspend fun `[`LifecycleOwner`](https://developer.android.com/reference/androidx/androidx/lifecycle/LifecycleOwner.html)`.onNextCreate(block: suspend `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`.() -> T): T?` [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleSuspendExt.kt#L30) +`suspend fun `[`LifecycleOwner`](https://developer.android.com/reference/androidx/androidx/lifecycle/LifecycleOwner.html)`.onNextCreate(block: suspend `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`.() -> T): T?` [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/suspend.kt#L30) -Executes [block](on-next-create.md#dispatch.android.lifecycle$onNextCreate(androidx.lifecycle.LifecycleOwner, kotlin.coroutines.SuspendFunction1((kotlinx.coroutines.CoroutineScope, dispatch.android.lifecycle.onNextCreate.T)))/block) one time, the next time the [Lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)'s state is at least [Lifecycle.State.CREATED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#CREATED). +Executes `block` one time, the next time the [Lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)'s state is at least [Lifecycle.State.CREATED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#CREATED). -If the lifecycle is already in this state, [block](on-next-create.md#dispatch.android.lifecycle$onNextCreate(androidx.lifecycle.LifecycleOwner, kotlin.coroutines.SuspendFunction1((kotlinx.coroutines.CoroutineScope, dispatch.android.lifecycle.onNextCreate.T)))/block) will be executed immediately. +If the lifecycle is already in this state, `block` will be executed immediately. ``` kotlin runBlocking { diff --git a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/androidx.lifecycle.-lifecycle-owner/on-next-resume.md b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/androidx.lifecycle.-lifecycle-owner/on-next-resume.md index d9fa235e2..ed76e8cce 100644 --- a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/androidx.lifecycle.-lifecycle-owner/on-next-resume.md +++ b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/androidx.lifecycle.-lifecycle-owner/on-next-resume.md @@ -2,11 +2,11 @@ # onNextResume -`suspend fun `[`LifecycleOwner`](https://developer.android.com/reference/androidx/androidx/lifecycle/LifecycleOwner.html)`.onNextResume(block: suspend `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`.() -> T): T?` [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleSuspendExt.kt#L78) +`suspend fun `[`LifecycleOwner`](https://developer.android.com/reference/androidx/androidx/lifecycle/LifecycleOwner.html)`.onNextResume(block: suspend `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`.() -> T): T?` [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/suspend.kt#L78) -Executes [block](on-next-resume.md#dispatch.android.lifecycle$onNextResume(androidx.lifecycle.LifecycleOwner, kotlin.coroutines.SuspendFunction1((kotlinx.coroutines.CoroutineScope, dispatch.android.lifecycle.onNextResume.T)))/block) one time, the next time the [Lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)'s state is at least [Lifecycle.State.RESUMED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#RESUMED). +Executes `block` one time, the next time the [Lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)'s state is at least [Lifecycle.State.RESUMED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#RESUMED). -If the lifecycle is already in this state, [block](on-next-resume.md#dispatch.android.lifecycle$onNextResume(androidx.lifecycle.LifecycleOwner, kotlin.coroutines.SuspendFunction1((kotlinx.coroutines.CoroutineScope, dispatch.android.lifecycle.onNextResume.T)))/block) will be executed immediately. +If the lifecycle is already in this state, `block` will be executed immediately. ``` kotlin runBlocking { diff --git a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/androidx.lifecycle.-lifecycle-owner/on-next-start.md b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/androidx.lifecycle.-lifecycle-owner/on-next-start.md index 87283dc11..ea6d4d1cc 100644 --- a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/androidx.lifecycle.-lifecycle-owner/on-next-start.md +++ b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/androidx.lifecycle.-lifecycle-owner/on-next-start.md @@ -2,11 +2,11 @@ # onNextStart -`suspend fun `[`LifecycleOwner`](https://developer.android.com/reference/androidx/androidx/lifecycle/LifecycleOwner.html)`.onNextStart(block: suspend `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`.() -> T): T?` [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleSuspendExt.kt#L54) +`suspend fun `[`LifecycleOwner`](https://developer.android.com/reference/androidx/androidx/lifecycle/LifecycleOwner.html)`.onNextStart(block: suspend `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`.() -> T): T?` [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/suspend.kt#L54) -Executes [block](on-next-start.md#dispatch.android.lifecycle$onNextStart(androidx.lifecycle.LifecycleOwner, kotlin.coroutines.SuspendFunction1((kotlinx.coroutines.CoroutineScope, dispatch.android.lifecycle.onNextStart.T)))/block) one time, the next time the [Lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)'s state is at least [Lifecycle.State.STARTED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#STARTED). +Executes `block` one time, the next time the [Lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)'s state is at least [Lifecycle.State.STARTED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#STARTED). -If the lifecycle is already in this state, [block](on-next-start.md#dispatch.android.lifecycle$onNextStart(androidx.lifecycle.LifecycleOwner, kotlin.coroutines.SuspendFunction1((kotlinx.coroutines.CoroutineScope, dispatch.android.lifecycle.onNextStart.T)))/block) will be executed immediately. +If the lifecycle is already in this state, `block` will be executed immediately. ``` kotlin runBlocking { diff --git a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/androidx.lifecycle.-lifecycle/index.md b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/androidx.lifecycle.-lifecycle/index.md index 8f91992dd..73e148caa 100644 --- a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/androidx.lifecycle.-lifecycle/index.md +++ b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/androidx.lifecycle.-lifecycle/index.md @@ -4,6 +4,6 @@ | Name | Summary | |---|---| -| [onNextCreate](on-next-create.md) | Executes [block](on-next-create.md#dispatch.android.lifecycle$onNextCreate(androidx.lifecycle.Lifecycle, kotlin.coroutines.SuspendFunction1((kotlinx.coroutines.CoroutineScope, dispatch.android.lifecycle.onNextCreate.T)))/block) one time, the next time the [Lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)'s state is at least [Lifecycle.State.CREATED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#CREATED).`suspend fun `[`Lifecycle`](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)`.onNextCreate(block: suspend `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`.() -> T): T?` | -| [onNextResume](on-next-resume.md) | Executes [block](on-next-resume.md#dispatch.android.lifecycle$onNextResume(androidx.lifecycle.Lifecycle, kotlin.coroutines.SuspendFunction1((kotlinx.coroutines.CoroutineScope, dispatch.android.lifecycle.onNextResume.T)))/block) one time, the next time the [Lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)'s state is at least [Lifecycle.State.RESUMED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#RESUMED).`suspend fun `[`Lifecycle`](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)`.onNextResume(block: suspend `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`.() -> T): T?` | -| [onNextStart](on-next-start.md) | Executes [block](on-next-start.md#dispatch.android.lifecycle$onNextStart(androidx.lifecycle.Lifecycle, kotlin.coroutines.SuspendFunction1((kotlinx.coroutines.CoroutineScope, dispatch.android.lifecycle.onNextStart.T)))/block) one time, the next time the [Lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)'s state is at least [Lifecycle.State.STARTED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#STARTED).`suspend fun `[`Lifecycle`](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)`.onNextStart(block: suspend `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`.() -> T): T?` | +| [onNextCreate](on-next-create.md) | Executes `block` one time, the next time the [Lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)'s state is at least [Lifecycle.State.CREATED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#CREATED).`suspend fun `[`Lifecycle`](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)`.onNextCreate(block: suspend `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`.() -> T): T?` | +| [onNextResume](on-next-resume.md) | Executes `block` one time, the next time the [Lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)'s state is at least [Lifecycle.State.RESUMED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#RESUMED).`suspend fun `[`Lifecycle`](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)`.onNextResume(block: suspend `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`.() -> T): T?` | +| [onNextStart](on-next-start.md) | Executes `block` one time, the next time the [Lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)'s state is at least [Lifecycle.State.STARTED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#STARTED).`suspend fun `[`Lifecycle`](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)`.onNextStart(block: suspend `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`.() -> T): T?` | diff --git a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/androidx.lifecycle.-lifecycle/on-next-create.md b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/androidx.lifecycle.-lifecycle/on-next-create.md index 1dfbd6524..9210f01d4 100644 --- a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/androidx.lifecycle.-lifecycle/on-next-create.md +++ b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/androidx.lifecycle.-lifecycle/on-next-create.md @@ -2,11 +2,11 @@ # onNextCreate -`suspend fun `[`Lifecycle`](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)`.onNextCreate(block: suspend `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`.() -> T): T?` [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleSuspendExt.kt#L42) +`suspend fun `[`Lifecycle`](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)`.onNextCreate(block: suspend `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`.() -> T): T?` [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/suspend.kt#L42) -Executes [block](on-next-create.md#dispatch.android.lifecycle$onNextCreate(androidx.lifecycle.Lifecycle, kotlin.coroutines.SuspendFunction1((kotlinx.coroutines.CoroutineScope, dispatch.android.lifecycle.onNextCreate.T)))/block) one time, the next time the [Lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)'s state is at least [Lifecycle.State.CREATED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#CREATED). +Executes `block` one time, the next time the [Lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)'s state is at least [Lifecycle.State.CREATED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#CREATED). -If the lifecycle is already in this state, [block](on-next-create.md#dispatch.android.lifecycle$onNextCreate(androidx.lifecycle.Lifecycle, kotlin.coroutines.SuspendFunction1((kotlinx.coroutines.CoroutineScope, dispatch.android.lifecycle.onNextCreate.T)))/block) will be executed immediately. +If the lifecycle is already in this state, `block` will be executed immediately. ``` kotlin runBlocking { diff --git a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/androidx.lifecycle.-lifecycle/on-next-resume.md b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/androidx.lifecycle.-lifecycle/on-next-resume.md index 6154c39be..f9974ac2d 100644 --- a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/androidx.lifecycle.-lifecycle/on-next-resume.md +++ b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/androidx.lifecycle.-lifecycle/on-next-resume.md @@ -2,11 +2,11 @@ # onNextResume -`suspend fun `[`Lifecycle`](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)`.onNextResume(block: suspend `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`.() -> T): T?` [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleSuspendExt.kt#L90) +`suspend fun `[`Lifecycle`](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)`.onNextResume(block: suspend `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`.() -> T): T?` [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/suspend.kt#L90) -Executes [block](on-next-resume.md#dispatch.android.lifecycle$onNextResume(androidx.lifecycle.Lifecycle, kotlin.coroutines.SuspendFunction1((kotlinx.coroutines.CoroutineScope, dispatch.android.lifecycle.onNextResume.T)))/block) one time, the next time the [Lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)'s state is at least [Lifecycle.State.RESUMED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#RESUMED). +Executes `block` one time, the next time the [Lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)'s state is at least [Lifecycle.State.RESUMED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#RESUMED). -If the lifecycle is already in this state, [block](on-next-resume.md#dispatch.android.lifecycle$onNextResume(androidx.lifecycle.Lifecycle, kotlin.coroutines.SuspendFunction1((kotlinx.coroutines.CoroutineScope, dispatch.android.lifecycle.onNextResume.T)))/block) will be executed immediately. +If the lifecycle is already in this state, `block` will be executed immediately. ``` kotlin runBlocking { diff --git a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/androidx.lifecycle.-lifecycle/on-next-start.md b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/androidx.lifecycle.-lifecycle/on-next-start.md index 18ec75c00..6219bb66d 100644 --- a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/androidx.lifecycle.-lifecycle/on-next-start.md +++ b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/androidx.lifecycle.-lifecycle/on-next-start.md @@ -2,11 +2,11 @@ # onNextStart -`suspend fun `[`Lifecycle`](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)`.onNextStart(block: suspend `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`.() -> T): T?` [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/LifecycleSuspendExt.kt#L66) +`suspend fun `[`Lifecycle`](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)`.onNextStart(block: suspend `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`.() -> T): T?` [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/suspend.kt#L66) -Executes [block](on-next-start.md#dispatch.android.lifecycle$onNextStart(androidx.lifecycle.Lifecycle, kotlin.coroutines.SuspendFunction1((kotlinx.coroutines.CoroutineScope, dispatch.android.lifecycle.onNextStart.T)))/block) one time, the next time the [Lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)'s state is at least [Lifecycle.State.STARTED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#STARTED). +Executes `block` one time, the next time the [Lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html)'s state is at least [Lifecycle.State.STARTED](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle/State.html#STARTED). -If the lifecycle is already in this state, [block](on-next-start.md#dispatch.android.lifecycle$onNextStart(androidx.lifecycle.Lifecycle, kotlin.coroutines.SuspendFunction1((kotlinx.coroutines.CoroutineScope, dispatch.android.lifecycle.onNextStart.T)))/block) will be executed immediately. +If the lifecycle is already in this state, `block` will be executed immediately. ``` kotlin runBlocking { diff --git a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/index.md b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/index.md index e975e3b4b..7eb54e0a8 100644 --- a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/index.md +++ b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/index.md @@ -6,7 +6,8 @@ | Name | Summary | |---|---| -| [LifecycleCoroutineScope](-lifecycle-coroutine-scope/index.md) | [MainImmediateCoroutineScope](https://rbusarow.github.io/Dispatch/dispatch-core/dispatch.core/-main-immediate-coroutine-scope/index.md) instance which is tied to a [Lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html).`class LifecycleCoroutineScope : `[`MainImmediateCoroutineScope`](https://rbusarow.github.io/Dispatch/dispatch-core/dispatch.core/-main-immediate-coroutine-scope/index.md) | +| [LifecycleCoroutineScope](-lifecycle-coroutine-scope/index.md) | [MainImmediateCoroutineScope](https://rbusarow.github.io/Dispatch/dispatch-core/dispatch.core/-main-immediate-coroutine-scope/index.md) which is tied to a [Lifecycle](https://developer.android.com/reference/androidx/androidx/lifecycle/Lifecycle.html).`open class LifecycleCoroutineScope : `[`MainImmediateCoroutineScope`](https://rbusarow.github.io/Dispatch/dispatch-core/dispatch.core/-main-immediate-coroutine-scope/index.md) | +| [LifecycleCoroutineScopeFactory](-lifecycle-coroutine-scope-factory/index.md) | Factory for [LifecycleCoroutineScope](-lifecycle-coroutine-scope/index.md)s. This may be injected into a lifecycle-aware class to provide custom [CoroutineContexts](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin.coroutines/-coroutine-context/index.html).`class LifecycleCoroutineScopeFactory` | ### Extensions for External Classes @@ -14,3 +15,9 @@ |---|---| | [androidx.lifecycle.Lifecycle](androidx.lifecycle.-lifecycle/index.md) | | | [androidx.lifecycle.LifecycleOwner](androidx.lifecycle.-lifecycle-owner/index.md) | | + +### Functions + +| Name | Summary | +|---|---| +| [MainImmediateContext](-main-immediate-context.md) | Default implementation of a [CoroutineContext](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin.coroutines/-coroutine-context/index.html) as seen in a `MainImmediateCoroutineScope`.`fun MainImmediateContext(): `[`CoroutineContext`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin.coroutines/-coroutine-context/index.html) | diff --git a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/kotlinx.coroutines.-coroutine-scope/index.md b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/kotlinx.coroutines.-coroutine-scope/index.md deleted file mode 100644 index d14241317..000000000 --- a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/kotlinx.coroutines.-coroutine-scope/index.md +++ /dev/null @@ -1,7 +0,0 @@ -[dispatch-android-lifecycle](../../index.md) / [dispatch.android.lifecycle](../index.md) / [kotlinx.coroutines.CoroutineScope](./index.md) - -### Extensions for kotlinx.coroutines.CoroutineScope - -| Name | Summary | -|---|---| -| [withViewLifecycle](with-view-lifecycle.md) | [CoroutineScope](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html) helper for a [Fragment](https://developer.android.com/reference/androidx/androidx/fragment/app/Fragment.html)'s [ViewLifecycleOwner](https://developer.android.com/reference/androidx/androidx/fragment/app/FragmentViewLifecycleOwner.html).`fun `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`.withViewLifecycle(fragment: `[`Fragment`](https://developer.android.com/reference/androidx/androidx/fragment/app/Fragment.html)`, block: `[`ViewLifecycleCoroutineScope`](../-view-lifecycle-coroutine-scope/index.md)`.() -> `[`Unit`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin/-unit/index.html)`): `[`Job`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-job/index.html) | diff --git a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/kotlinx.coroutines.-coroutine-scope/with-view-lifecycle.md b/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/kotlinx.coroutines.-coroutine-scope/with-view-lifecycle.md deleted file mode 100644 index bf73db27b..000000000 --- a/docs/kdoc/dispatch-android-lifecycle/dispatch.android.lifecycle/kotlinx.coroutines.-coroutine-scope/with-view-lifecycle.md +++ /dev/null @@ -1,27 +0,0 @@ -[dispatch-android-lifecycle](../../index.md) / [dispatch.android.lifecycle](../index.md) / [kotlinx.coroutines.CoroutineScope](index.md) / [withViewLifecycle](./with-view-lifecycle.md) - -# withViewLifecycle - -`@ExperimentalCoroutinesApi fun `[`CoroutineScope`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html)`.withViewLifecycle(fragment: `[`Fragment`](https://developer.android.com/reference/androidx/androidx/fragment/app/Fragment.html)`, block: `[`ViewLifecycleCoroutineScope`](../-view-lifecycle-coroutine-scope/index.md)`.() -> `[`Unit`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin/-unit/index.html)`): `[`Job`](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-job/index.html) [(source)](https://github.com/RBusarow/Dispatch/tree/master/dispatch-android-lifecycle/src/main/java/dispatch/android/lifecycle/ViewLifecycleCoroutineScope.kt#L64) - -[CoroutineScope](https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines/-coroutine-scope/index.html) helper for a [Fragment](https://developer.android.com/reference/androidx/androidx/fragment/app/Fragment.html)'s [ViewLifecycleOwner](https://developer.android.com/reference/androidx/androidx/fragment/app/FragmentViewLifecycleOwner.html). - -This function observes a `Fragment`'s [viewLifecycleOwnerLiveData](https://developer.android.com/reference/androidx/androidx/fragment/app/Fragment.html#getViewLifecycleOwnerLiveData()), -and invokes [block](with-view-lifecycle.md#dispatch.android.lifecycle$withViewLifecycle(kotlinx.coroutines.CoroutineScope, androidx.fragment.app.Fragment, kotlin.Function1((dispatch.android.lifecycle.ViewLifecycleCoroutineScope, kotlin.Unit)))/block). - -``` kotlin -class MyFragment @Inject constructor( - val scope: MainImmediateCoroutineScope -) : Fragment() { - - val myViewModel by viewModels() - - val observerJob = scope.withViewLifecycle(this) { - // this lambda is invoked every time the View lifecycle is set - myViewModel.dataFlow.onEach { data -> - // ... - }.launchOnCreate() - } -} -``` - diff --git a/docs/modules/dispatch-android-lifecycle-extensions.md b/docs/modules/dispatch-android-lifecycle-extensions.md index 3a7ad72fd..80cd46feb 100644 --- a/docs/modules/dispatch-android-lifecycle-extensions.md +++ b/docs/modules/dispatch-android-lifecycle-extensions.md @@ -51,7 +51,7 @@ class SomeApplication : Application() { override fun onCreate() { super.onCreate() // A custom factory can be set to add elements to the CoroutineContext - LifecycleScopeFactory.set { MainImmediateCoroutineScope() + SomeCustomElement() } + LifecycleScopeFactory.set { MainImmediateProvidedCoroutineContext() + SomeCustomElement() } } } ``` @@ -62,13 +62,13 @@ class SomeEspressoTest { fun setUp() { // This custom factory can be used to use custom scopes for testing, // such as an idling dispatcher - LifecycleScopeFactory.set { MainImmediateIdlingCoroutineScope() } + LifecycleScopeFactory.set { MainImmediateIdlingCoroutineScope().coroutineContext } } @After fun tearDown() { // The factory can also be reset to default - LifecycleScopeFactory.reset() + LifecycleCoroutineScopeFactory.reset() } } ``` @@ -93,7 +93,7 @@ class SomeFragmentEspressoTest { fun setUp() { // set a custom factory which is applied to all newly created lifecycleScopes LifecycleScopeFactory.set { - MainImmediateCoroutineScope() + idlingRule.dispatcherProvider + MainImmediateProvidedCoroutineContext() + idlingRule.dispatcherProvider } // now SomeFragment will use an IdlingDispatcher in its CoroutineScope From 992eea73c43709586deace57f56ba95a46fce575 Mon Sep 17 00:00:00 2001 From: Rick Busarow Date: Sat, 11 Jul 2020 22:06:49 -0500 Subject: [PATCH 5/5] MainImmediateProvidedContext -> MainImmediateContext --- .../dispatch/android/lifecycle/LifecycleScopeFactoryTest.kt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/dispatch-android-lifecycle-extensions/src/test/java/dispatch/android/lifecycle/LifecycleScopeFactoryTest.kt b/dispatch-android-lifecycle-extensions/src/test/java/dispatch/android/lifecycle/LifecycleScopeFactoryTest.kt index 19acb1f9d..c1780c199 100644 --- a/dispatch-android-lifecycle-extensions/src/test/java/dispatch/android/lifecycle/LifecycleScopeFactoryTest.kt +++ b/dispatch-android-lifecycle-extensions/src/test/java/dispatch/android/lifecycle/LifecycleScopeFactoryTest.kt @@ -60,7 +60,7 @@ internal class LifecycleScopeFactoryTest : HermitJUnit5() { } @Test - fun `default factory should be a default MainImmediateProvidedContext`() = runBlockingTest { + fun `default factory should be a default MainImmediateContext`() = runBlockingTest { val scope = LifecycleScopeFactory.create(lifecycleOwner.lifecycle)