When I use ```private val presenter: MyFeaturePres...
# koin-contributors
p
When I use
Copy code
private val presenter: MyFeaturePresenter by scope.inject()
Sometimes I got the crash
Copy code
Caused by: java.lang.IllegalStateException: Fragment MyFeatureFragment{e397a0b} (4be986d3-729a-430d-86ee-ee1f657be059) not attached to an activity.
    at androidx.fragment.app.Fragment.requireActivity(Fragment.java:995)
    at org.koin.androidx.scope.FragmentExtKt.createFragmentScope(FragmentExt.kt:38)
    at org.koin.androidx.scope.FragmentExtKt$fragmentScope$1.invoke(FragmentExt.kt:50)
    at org.koin.androidx.scope.FragmentExtKt$fragmentScope$1.invoke(FragmentExt.kt:50)
    at kotlin.SynchronizedLazyImpl.getValue(LazyJVM.kt:74)
Why? Because this value
val
is initializing in
init
from Kotlin fragment class. How to avoid that
Copy code
private val presenter: MyFeaturePresenter by lazy { scope.get() }
Is it the expected scenario to Koin lazy injection? šŸ¤”
m
Iā€™m not sure if Koin can avoid the
requireActivity
, after all the Fragment scope is a child from the
Activity
(see
scope.linkTo
in the code snippet you posted). Ignoring that would break the relationship between these two scopes. Your proposed solution seems off. Arenā€™t
inject
lazy by default? Wrapping it inside a
lazy
should not change the behaviour. Check the last line of you stack trace
SynchronizedLazyImpl.getValue
. What do you mean by ā€œval is initialized in initā€? Do you have a code sample for this statement?
a
You should use `AndroidScopeComponent`interface. this way just use the i`nject()` function, directly with the right scope
also look at
ScopeFragment
class
p
Iā€™m using
ScopeActivity
and
ScopeFragment
. I donā€™t know yet how can reproduce this error, but Iā€™m getting him sometimes in Firebase Crashlytics. My guess: sometimes fragment is initializing ā€œtoo fastā€ and is not attached to activity yet, so requireActivity() throws an exception.
a
About ScopeFragment it was one problem we had, that scope couldnā€™t be attached. In latest version itā€™s now solved
p
hummmā€¦ Iā€™m using
3.3.1
, what version has it fixed?
a
you have it šŸ˜…
yes, your Activity is not yet attached
this mean you try to do something in a property that is initialized, before any onCreate call
p
Yes, thatā€™s the problem! Iā€™m doing something wrong in Koin usage? In my mind, that was a expected usage without crash, of course
I wrote an article in Medium platform about this error and how can avoid it. But, the doubt about usage continues. šŸ™ƒ
m
As a rule of thumb, there is no scenario in which you want to do any operation on a Fragment or Activity initialization time. Those components are created with an incomplete state, and only later will receive their respective contexts and required dependencies. That is why they offer you an
onCreate
and that is where your Fragment initialization logic should go to ensure your Fragment is in a safe state. If you use
lazy
, you should ensure it is only called "after"
onCreated
state is reached or you likely will crash.
p
I agree totally with you @Marcello Galhardo. And
inject
in Koin usage is lazy and can handle this kind. The problem is when you trigger a combination of
createScope()->requireActivity()
because you just added a
fragmentScope()
. And youā€™re not expecting that šŸ˜….
Backing to my initial question...
Is it the expected scenario to Koin lazy injection?
I think itā€™s not expected get a crash when youā€™re using
scope.injection
. Maybe we need to improve docs, or annotate it with as throwable. I really donā€™t know right know a better solution to help developers with Koin dev experience.
a
Maybe we need to improve docs, or annotate it with as throwable.
yes documentation can be improved on this point šŸ‘
p
Nice @arnaud.giuliani, Iā€™ll do it ASAP! šŸ˜‰
a
great, thanks šŸ™‚ Ping me on the issue/PR