添加链接
link管理
链接快照平台
  • 输入网页链接,自动生成快照
  • 标签化管理网页链接

As Kotlin Multiplatform is becoming an increasingly popular choice for cross-platform development, developers face the task of selecting a suitable dependency-injection library for their KMP projects. We’re here to introduce Koin and Kotlin-inject , two libraries that take different approaches to solving this problem.

interface WeatherApiService {   @GET("weather")   suspend fun getWeatherData(@Query("city") city: String): WeatherData // GetWeatherDataInteractor.kt class GetWeatherDataInteractor(private val weatherApiService: WeatherApiService) : Interactors.GetWeatherData {   override suspend operator fun invoke(city: String): WeatherData {     return weatherApiService.getWeatherData(city) // WeatherRepository.kt class WeatherRepository(private val getWeatherInteractor: Interactors.GetWeatherData) : Repositories.Weather {   override suspend fun fetch(city: String): Weather {     return getWeatherInteractor(city).mapToLocal() // GetWeatherUseCase.kt class GetWeatherUseCase(private val weatherRepository: Repositories.Weather) : UseCases.GetWeather {   override suspend operator fun invoke(city: String): Weather {     return weatherRepository.fetch(city)
  • Kotlin-based dependency injection library that offers a user-friendly experience through its easy-to-read Kotlin DSL
  • Suitable for any Kotlin application, including Android, Multiplatform, or Backend development
  • Easily integrates with the ViewModel, Ktor, and Compose, which adds to Koin’s appeal across diverse developer domains
val interactorsModule = module {   includes(servicesModule)   factory<Interactors.GetWeatherData> {       GetWeatherDataInteractor(get())  // RepositoriesModule.kt val repositoriesModule = module {   includes(interactorsModule)   single<Repositories.Weather> {       WeatherRepository(get())  // UseCasesModule.kt val useCasesModule = module {   includes(repositoriesModule)   factory<UseCases.GetWeather> {       GetWeatherUseCase(get())

The factory function binds implementations to interfaces and the function get() helps Koin retrieve injected dependencies during runtime. In the code snippet below, we’re instructing Koin on how to build a UseCases.GetWeather instance. It uses the get() function to obtain the necessary Repositories.Weather dependency that GetWeatherUseCase requires:

  • Relatively new and simple Kotlin-based dependency-injection library
  • Powered by Kotlin’s robust features like KSP and lazy initialization, which simplify the process of providing dependencies
  • With the use of Kotlin typealias, it allows injecting multiple instances of the same type and even supports lambda injection
@Provides   protected fun provideWeatherApiService(): WeatherApiService =      WeatherServiceProvider.provide() // InteractorsComponent.kt interface InteractorsComponent : ServicesComponent {   @Provides   protected fun GetWeatherDataInteractor.bind(): Interactors.GetWeatherData = this // RepositoriesComponent.kt interface RepositoriesComponent : InteractorsComponent {   @ExampleScope   @Provides   protected fun WeatherRepository.bind(): Repositories.Weather = this // UseCasesComponent.kt interface UseCasesComponent : RepositoriesComponent {   @Provides   protected fun GetWeatherUseCase.bind(): UseCases.GetWeather = this // ExampleComponent.kt @ExampleScope @Component abstract class ExampleComponent : UseCasesComponent {   abstract val getWeatherUseCase: UseCases.GetWeather interface RepositoriesComponent : InteractorsComponent {   // provide repository dependencies interface UseCasesComponent : RepositoriesComponent {   // provide usecase dependencies @ExampleScope @Component abstract class ExampleComponent : UseCasesComponent { // Koin // Startup time: 0.2475 ms val exampleKoin = startKoin { modules(useCasesModule) }.koin // Injection time: 0.0137 ms val weatherUseCase = exampleKoin.get<UseCases.GetWeather>() // Kotlin-inject // Startup time: 0.0005 ms val exampleComponent = ExampleComponent::class.create() // Injection time: 0.0043 ms val weatherUseCase = exampleComponent.getWeatherUseCase

In summary, while Koin offers quicker build times, it does come with a trade-off. The runtime dependency resolution impacts the overall performance, causing Koin to lag significantly behind Kotlin-inject in this regard . The difference is most noticeable during startup. Resolving the Koin dependency graph requires significantly more time compared to creating a Kotlin-inject component, which benefits from pre-generated boilerplate code.

Now, let’s delve into the libraries’ debugging capabilities. Both libraries excel in providing clear and informative error descriptions. However, Kotlin-inject has the advantage of showing them at compile-time , which allows you to correct your mistakes without ever running the application. This is not only a more convenient but also a much safer approach. On the other hand, Koin addresses this with somewhat of a workaround – writing tests to validate your Koin setup :

Koin has an active community of contributors ensuring regular updates and enhancements. After all, they’ve paved the way for smooth integrations with Ktor, Compose, ViewModel, and KMP and will continue to provide support for future technologies. Alongside regular updates and initiatives, Koin’s engaged user community helps spot and resolve issues quickly. On the other hand, Kotlin-inject is still establishing its presence with a smaller contributor base. However, it’s gaining traction within the Kotlin development scene, hinting at a bright future for the community.

Implementing IoT Device Onboarding in Mobile Apps

Discover what challenges to expect when implementing IoT device onboarding in a mobile app and how to approach them best.

Karlo Čeh

Panda CSS – CSS-in-JS without Runtime Overhead

With its simplified approach to front-end styling, Panda CSS can help you streamline your development workflow and create efficient web applications.

Ivica Batinić

A Crash Course in Augmented Reality on iOS with ARKit

Since the release of ARKit in 2017., and especially the 2.0 announcement during the WWDC 2018 conference, I’ve been interested in what it can provide.

Goran Brlas

We use cookies to optimise and continuously improve our website for individual users like you. By clicking “Accept all”, you accept storing of cookies on your device. Find out more at our Privacy Policy

Manage
Accept all