Kotlin org.koin.core.error.InstanceCreationException:无法为[Factory:';com.pokemonsearch.presentation.search.SearchViewModel';]创建实例
我在Kotlin应用程序中使用Koin作为依赖注入框架。我正在尝试使用协同程序将数据保存到房间数据库。我有一个从viewmodel调用的用例“AddToFavourite”类。运行应用程序时,应用程序崩溃,出现以下错误。当我检查时,我知道koin找不到依赖关系。谁能帮我一个解决办法吗。请在下面找到存储库、用例、视图模型、数据库和di模块 进程:com.debin.pokemonsearch,PID:16027 java.lang.RuntimeException:无法启动活动组件信息{com.debin.pokemonsearch/com.debin.pokemonsearch.HomeActivity}:org.koin.core.error.InstanceCreationException:无法为[Factory:'com.debin.pokemonsearch.presentation.search.SearchViewModel'创建实例 在android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2817` 位于android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2892) 位于android.app.ActivityThread.-wrap11(未知来源:0) 在android.app.ActivityThread$H.handleMessage(ActivityThread.java:1593) 位于android.os.Handler.dispatchMessage(Handler.java:105) 位于android.os.Looper.loop(Looper.java:164) 位于android.app.ActivityThread.main(ActivityThread.java:6541) 位于java.lang.reflect.Method.invoke(本机方法) 在com.android.internal.os.Zygote$MethodAndArgsCaller.run上(Zygote.java:240) 位于com.android.internal.os.ZygoteInit.main(ZygoteInit.java:767) 原因:org.koin.core.error.InstanceCreationException:无法为[Factory:'com.debin.pokemonsearch.presentation.search.SearchViewModel']创建实例 位于org.koin.core.instance.InstanceFactory.create(InstanceFactory.kt:59) 位于org.koin.core.instance.FactoryInstanceFactory.get(FactoryInstanceFactory.kt:36) 位于org.koin.core.registry.InstanceRegistry.resolveInstance$koin_core(InstanceRegistry.kt:87) 位于org.koin.core.scope.scope.resolveInstance(scope.kt:214) 位于org.koin.core.scope.scope.get(scope.kt:181) 在org.koin.android.viewmodel.ViewModelFactoryKt$defaultViewModelFactory$1.create(ViewModelFactory.kt:13)上 位于androidx.lifecycle.ViewModelProvider.get(ViewModelProvider.java:187) 位于androidx.lifecycle.ViewModelProvider.get(ViewModelProvider.java:150) 位于org.koin.android.viewmodel.ViewModelResolutionKt.get(ViewModelResolution.kt:21) 位于org.koin.android.viewmodel.ViewModelResolutionKt.resolveInstance(ViewModelResolution.kt:10) 位于org.koin.android.viewmodel.scope.ScopeExtKt.getViewModel(ScopeExt.kt:68) 位于org.koin.android.viewmodel.scope.ScopeExtKt.getViewModel(ScopeExt.kt:56) 位于org.koin.android.viewmodel.koin.KoinExtKt.getViewModel(KoinExt.kt:34) 位于org.koin.android.viewmodel.ext.android.ViewModelStoreOwnerExtKt.getViewModel(ViewModelStoreOwnerExt.kt:66) 在com.debin.pokemonsearch.presentation.search.SearchFragment$$special$$inlined$viewModel$1.invoke(ViewModelStoreOwnerExt.kt:71) 位于com.debin.pokemonsearch.presentation.search.SearchFragment$$special$$inlined$viewModel$1.invoke(未知源:0) 在kotlin.UnsafeLazyImpl.getValue处(Lazy.kt:81) 位于com.debin.pokemonsearch.presentation.search.SearchFragment.getViewModel(未知来源:2) 在com.debin.pokemonsearch.presentation.search.SearchFragment.observePokemon上(SearchFragment.kt:39) 在com.debin.pokemonsearch.presentation.search.SearchFragment.onViewCreated上(SearchFragment.kt:31) 位于androidx.fragment.app.FragmentStateManager.createView(FragmentStateManager.java:332) 位于androidx.fragment.app.FragmentManager.moveToState(FragmentManager.java:1187) 位于androidx.fragment.app.FragmentManager.moveToState(FragmentManager.java:1356) 位于androidx.fragment.app.FragmentManager.moveFragmentToExpectedState(FragmentManager.java:1434) 位于androidx.fragment.app.FragmentManager.moveToState(FragmentManager.java:1497) 位于androidx.fragment.app.FragmentManager.dispatchStateChange(FragmentManager.java:2625) 位于androidx.fragment.app.FragmentManager.dispatchActivityCreated(FragmentManager.java:2577) 位于androidx.fragment.app.fragment.performActivityCreated(fragment.java:2722) 位于androidx.fragment.app.FragmentStateManager.activityCreated(FragmentStateManager.java:346) 位于androidx.fragment.app.FragmentManager.moveToState(FragmentManager.java:1188) 位于androidx.fragment.app.FragmentManager.moveToState(FragmentManager.java:1356) 位于androidx.fragment.app.FragmentManager.moveFragmentToExpectedState(FragmentManager.java:1434) 位于androidx.fragment.app.FragmentManager.moveToState(FragmentManager.java:1497) 2021-01-24 19:49:54.088 16027-16027/com.debin.pokemonsearch E/AndroidRuntime:at-androidx.fragment.app.FragmentManager.dispatchStateChange(FragmentManager.java:2625) 位于androidx.fragment.app.FragmentManager.dispatchActivityCreated(FragmentManager.java:2577) 位于androidx.fragment.app.FragmentController.dispatchActivityCreated(FragmentController.java:247) 位于androidx.fragment.app.FragmentActivity.onStart(FragmentActivity.java:541) 在androidx.appcompat.app.AppCompatActivity.onStart(AppCompatActivity.java:210)上 位于android.app.Instrumentation.callActivityOnStart(Instrumentation.java:1333) 位于android.app.Activity.performStart(Activity.java:6992) 在android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2780)上 …还有9个 原因:org.koin.core.error.InstanceCreationException:无法为[Factory:'com.debin.pokemonsearch.pokemoncore.interactions.AddToFavourites'创建实例 位于org.koin.core.instance.InstanceFactory.create(InstanceFactory.kt:59) 位于org.koin.core.instance.FactoryInstanceFactory.get(FactoryInstanceFactory.kt:36) 位于org.koin.core.registry.InstanceRegistry.resolveInstance$koin_core(InstanceRegistry.kt:87) 位于org.koin.core.scope.scope.resolveInstance(scope.kt:214) 位于org.koin.core.scope.scope.get(scope.kt:181) 在com.debin.pokemonsearch.di.ViewModelModuleKt$viewModelModule$1$1.invoke(viewModelModule.kt:24) 在com.debin.pokemonsearch.di.ViewModelModuleKt$viewModelModule$1$1.invoke(未知来源:4) A.Kotlin org.koin.core.error.InstanceCreationException:无法为[Factory:';com.pokemonsearch.presentation.search.SearchViewModel';]创建实例,kotlin,android-room,kotlin-coroutines,koin,Kotlin,Android Room,Kotlin Coroutines,Koin,我在Kotlin应用程序中使用Koin作为依赖注入框架。我正在尝试使用协同程序将数据保存到房间数据库。我有一个从viewmodel调用的用例“AddToFavourite”类。运行应用程序时,应用程序崩溃,出现以下错误。当我检查时,我知道koin找不到依赖关系。谁能帮我一个解决办法吗。请在下面找到存储库、用例、视图模型、数据库和di模块 进程:com.debin.pokemonsearch,PID:16027 java.lang.RuntimeException:无法启动活动组件信息{com.d
class AddToFavourites(private val coreRepository: IPokemonCoreRepository) {
suspend fun invokeAddToFavourites(pokemon: Pokemon) {
coreRepository.addPokemonToFavourites(pokemon)
}
}
interface IPokemonCoreRepository {
suspend fun addPokemonToFavourites(pokemon: Pokemon)
suspend fun getFavouritePokemon() : List<Pokemon>
suspend fun removePokemonFromFavourite(pokemon: Pokemon)
}
data class Pokemon(
val id : Int,
val name : String,
val description : String,
val imageUrl : String
)
class PokemonCoreRepository(private val dataSource: PokemonCoreDataSource) : IPokemonCoreRepository {
override suspend fun addPokemonToFavourites(pokemon: Pokemon) {
return dataSource.addPokemonToFavourites(pokemon)
}
override suspend fun getFavouritePokemon(): List<Pokemon> {
return dataSource.getFavouritePokemon()
}
override suspend fun removePokemonFromFavourite(pokemon: Pokemon) {
return dataSource.removePokemonFromFavourite(pokemon)
}
}
interface PokemonCoreDataSource {
suspend fun addPokemonToFavourites(pokemon: Pokemon)
suspend fun getFavouritePokemon() : List<Pokemon>
suspend fun removePokemonFromFavourite(pokemon: Pokemon)
}
class PokemonCoreDataSourceImpl(private val database : PokemonDatabase) : PokemonCoreDataSource{
override suspend fun addPokemonToFavourites(pokemon: Pokemon) {
return database.pfDao.addToFavourite(PokemonFavouriteEntity(id = pokemon.id, name = pokemon.name,
description = pokemon.description, imageUrl = pokemon.imageUrl))
}
override suspend fun getFavouritePokemon(): List<Pokemon> {
return database.pfDao.getFavouritePokemon().map {
Pokemon(id = it.id, name = it.name, description = it.description, imageUrl = it.imageUrl)
}
}
override suspend fun removePokemonFromFavourite(pokemon: Pokemon) {
return database.pfDao.removeFromFavourite(PokemonFavouriteEntity(
id = pokemon.id, name = pokemon.name,
description = pokemon.description, imageUrl = pokemon.imageUrl
))
}
}
val useCaseModule = module {
factory { AddToFavourites(get()) }
factory { GetFavourites(get()) }
factory { RemoveFromFavourite(get()) }
}
val repositoryModule = module {
single<IPokemonCoreRepository> { PokemonCoreRepository(get()) }
}
val dataSourceModule = module {
single<PokemonCoreDataSource> { PokemonCoreDataSourceImpl(get()) }
}
val databaseModule = module {
single { PokemonDatabaseFactory.getDBInstance(get()) }
}
val viewModelModule = module {
viewModel { SearchViewModel(get(), get(), get()) }
}
@Database(entities = [PokemonFavouriteEntity::class], version = 1, exportSchema = false)
abstract class PokemonDatabase : RoomDatabase() {
abstract val pfDao : PokemonFavouriteDao
}
object PokemonDatabaseFactory {
fun getDBInstance(context: Context) {
Room.databaseBuilder(context, PokemonDatabase::class.java, "PokemonDB")
.fallbackToDestructiveMigration()
.build()
}
}
@Dao
interface PokemonFavouriteDao {
@Insert(onConflict = REPLACE)
suspend fun addToFavourite(pokemon : PokemonFavouriteEntity)
}
@Entity(tableName = "favourites")
data class PokemonFavouriteEntity(
@PrimaryKey(autoGenerate = true) val id : Int,
@ColumnInfo(name = "pokemonName") val name : String = "",
@ColumnInfo(name = "pokemonDescription") val description : String = "",
@ColumnInfo(name = "pokemonImage")val imageUrl : String = ""
)
class SearchViewModel (private val getPokemonDescription: GetPokemonDescription,
private val getPokemonSprites: GetPokemonSprites,
private val addToFavourites: AddToFavourites) : ViewModel() {
private val _pokemon = MutableLiveData<Resource<PokemonResponse>>()
private val _pokemonSprites = MutableLiveData<Resource<List<String>>>()
private val _pokemonSpecies = MutableLiveData<Resource<PokemonSpeciesResponse>>()
val pokemon : LiveData<Resource<PokemonResponse>> get() = _pokemon
val pokemonSpecies : LiveData<Resource<PokemonSpeciesResponse>> get() = _pokemonSpecies
fun getPokemonDetails(pokemonName : String) {
_pokemon.value = Resource.Loading()
getPokemonSprites.execute(PokemonSubscriber(), pokemonName)
}
fun getPokemonSpeciesDetails(pokemonName : String) {
_pokemonSpecies.value = Resource.Loading()
getPokemonDescription.execute(PokemonSpeciesSubscriber(), pokemonName)
}
fun addToFavourite() {
viewModelScope.launch {
withContext(Dispatchers.IO) {
addToFavourites.invokeAddToFavourites(getPokemonDetails())
}
}
}
inner class PokemonSubscriber : DisposableSingleObserver<PokemonResponse>() {
override fun onSuccess(pokemonResponse: PokemonResponse) {
_pokemon.value = Resource.Success(pokemonResponse)
}
override fun onError(error: Throwable) {
_pokemon.value = Resource.Error(error.message)
}
}
inner class PokemonSpeciesSubscriber : DisposableSingleObserver<PokemonSpeciesResponse>() {
override fun onSuccess(pokemonSpeciesResponse: PokemonSpeciesResponse) {
_pokemonSpecies.value = Resource.Success(pokemonSpeciesResponse)
}
override fun onError(error: Throwable) {
_pokemonSpecies.value = Resource.Error(error.message)
}
}
private fun getPokemonDetails() : Pokemon {
var pokemonId = 0
var pokemonName = ""
var pokemonDescription = ""
var pokemonImage = ""
_pokemon.observeForever {
when(it) {
is Resource.Success -> {
pokemonImage = it.result.sprites.front_default
}
else -> {
}
}
}
_pokemonSpecies.observeForever {
when(it) {
is Resource.Success -> {
pokemonId = it.result.id
pokemonName = it.result.name
pokemonDescription = it.result.flavor_text_entries[0].flavor_text
}
else -> {
}
}
}
return Pokemon(pokemonId, pokemonName, pokemonDescription, pokemonImage)
}
override fun onCleared() {
super.onCleared()
getPokemonDescription.dispose()
getPokemonSprites.dispose()
}
object PokemonDatabaseFactory {
fun getDBInstance(context: Context) =
Room.databaseBuilder(context, PokemonDatabase::class.java, "PokemonDB")
.fallbackToDestructiveMigration()
.build()
}
single {
Room.databaseBuilder(context, PokemonDatabase::class.java, "PokemonDB")
.fallbackToDestructiveMigration()
.build()
}