InsertKoinIO / koin

Koin - a pragmatic lightweight dependency injection framework for Kotlin & Kotlin Multiplatform
https://insert-koin.io
Apache License 2.0
9.04k stars 718 forks source link

How to use Scope feature 2.2.0 in DialogFragment? #951

Closed egorikftp closed 2 years ago

egorikftp commented 3 years ago

Previously we are able to inject dependencies with following way.

  1. We create scope for DialogFragment image

  2. Inject scoped dependencies image

How to achieve the same behaviour with the new library version?

arnaudgiuliani commented 3 years ago

use the KoinScopeComponent:

https://doc.insert-koin.io/#/koin-core/scopes?id=scope-component-associate-a-scope-to-a-component-220

egorikftp commented 3 years ago

Worked solution is

abstract class ScopeDialogFragment : AppCompatDialogFragment(), KoinScopeComponent {

    override val scope: Scope by lazy { newScope(this) }

    override fun onDestroy() {
        closeScope()
        super.onDestroy()
    }
class ThemeSettingDialogFragment : ScopeDialogFragment() {

    private val viewModel: ThemeViewModel by inject()

    //Other code
}

As for me it looks not clear why for viewModel I should use inject?

For example in ScopeFragment I'm able to use like this

val photoReportModule = module {

    scope<PhotoReportFragment> {
        scoped { PhotoReportRepository(firebase = get()) }
        scoped { PhotoReportUseCase(photoReportRepository = get()) }

        viewModel {
            PhotoReportViewModel(
                    photoReportUseCase = get(),
                    analytics = get()
            )
        }
    }
}

import org.koin.androidx.viewmodel.ext.android.viewModel

class PhotoReportFragment : ScopeFragment(R.layout.fragment_photo_report), PhotoReportsFeature {

    private val viewModel by viewModel<PhotoReportViewModel>()

    //other code
}
MedveDomg commented 3 years ago

@egorikftp I'm trying to use scoped viewmodel in just regular fragment, but get an error Caused by: org.koin.core.error.NoBeanDefFoundException: No definition found for class, but your solution with inject didn't produce any error, but main feature of viewmodel doesn't work.

MedveDomg commented 3 years ago

I fixed issue on my side by changing dependency of scope library (I was using not android x) and extends from ScopeActivity for launch my ScopeFragment. Thanks everybody.

sebastienrouif commented 3 years ago

@arnaudgiuliani is there a plan to make a ScopeDialogFragment ?

sebastienrouif commented 3 years ago

actually, we are missing contentProviders and BroadcastReceivers too as they are application components too https://developer.android.com/guide/components/fundamentals#Components I'm happy to help with the PR

alessandroToninelli commented 3 years ago

I have the same issue. With This components


 scope<MainActivity> {
           scope<EditCartItemDialog> {
                    viewModel<EditCartItemViewModel>()
                  }
}

I have to call inject instead of viewModel otherwise i have the error: org.koin.core.error.NoBeanDefFoundException: No definition found for class:'com.toninelli.ton_store.ui.main.cart.EditCartItemViewModel'. Check your definitions!


class EditCartItemDialog(
) : BottomSheetDialogFragment(), KoinScopeComponent {

    override val scope: Scope by lazy { newScope() }

    private val model by inject<EditCartItemViewModel>()
arnaudgiuliani commented 3 years ago

@alessandroToninelli can you try to avoid inner scope definition. Is it better?

scope<MainActivity> {

}
scope<EditCartItemDialog> {
         viewModel<EditCartItemViewModel>()
}
arnaudgiuliani commented 3 years ago

if you use inject for ViewModel, it won't be wired to Android lfecycle factories

alessandroToninelli commented 3 years ago

avoiding inner scopes the issue persists, I have to use inject otherwise the app crashes with the same exception

org.koin.core.error.NoBeanDefFoundException: No definition found for class:'com.toninelli.ton_store.ui.main.cart.EditCartItemViewModel'. Check your definitions!

gurgen-arustamyan commented 3 years ago

@arnaudgiuliani is there a plan to make a ScopeDialogFragment, ScopeBottomSheetDialogFragment...?

stale[bot] commented 2 years ago

This issue has been automatically marked as stale because it has not had recent activity. It will be closed if no further activity occurs. Thank you for your contributions.