Migrate db class from Java to Kotlin

Java DB class:

@Singleton
@Database(entities = { Article.class }, version = 1)
public abstract class AppDatabase extends RoomDatabase {
    public static final String DATABASE_NAME = "app_database";
    public abstract ArticlesDao articlesDao();
}

convert to Kotlin:

@Singleton
@Database(entities = [Article::class], version = 1)
abstract class AppDatabase : RoomDatabase() {
    abstract fun articlesDao(): ArticlesDao
}

数据库名字常量可以定义在一个单独的文件内 Constants.kt

const val DATABASE_NAME = "android-architecture-db"

遇到如下问题:

RuntimeException: cannot find implementation for AppDatabase. AppDatabase_Impl does not exist

解决办法:https://stackoverflow.com/a/51913796/2722270

Kotlinlang Tutorials - Android Frameworks Using Annotation Processing In Kotlin you specify the dependencies in a similar to Java way using Kotlin Annotation processing tool (kapt) instead of annotationProcessor.

Then I modified the build.gradle(Module:app) by changing all annotationProcessor to kapt, it works:

--- a/app/build.gradle
+++ b/app/build.gradle
@@ -2,6 +2,8 @@ apply plugin: 'com.android.application'

 apply plugin: 'kotlin-android'
+apply plugin: 'kotlin-kapt'
 apply plugin: 'kotlin-android-extensions'

 android {
     // Butter Knife
     implementation "com.jakewharton:butterknife:$butterknife_version"
-    annotationProcessor "com.jakewharton:butterknife-compiler:$butterknife_version"
+    kapt "com.jakewharton:butterknife-compiler:$butterknife_version"

     // Room
     implementation "android.arch.persistence.room:runtime:$arch_lifecycle_version"
-    annotationProcessor "android.arch.persistence.room:compiler:$arch_lifecycle_version"
+    kapt "android.arch.persistence.room:compiler:$arch_lifecycle_version"
     // LifeCycle
     implementation "android.arch.lifecycle:runtime:$arch_lifecycle_version"
     implementation "android.arch.lifecycle:extensions:$arch_lifecycle_version"
     implementation "android.arch.lifecycle:common-java8:$arch_lifecycle_version"
-    annotationProcessor "android.arch.lifecycle:compiler:$arch_lifecycle_version"
+    kapt "android.arch.lifecycle:compiler:$arch_lifecycle_version"

     // Dagger
     implementation "com.google.dagger:dagger:$dagger_version"
     implementation "com.google.dagger:dagger-android-support:$dagger_version"
-    annotationProcessor "com.google.dagger:dagger-compiler:$dagger_version"
-    annotationProcessor "com.google.dagger:dagger-android-processor:$dagger_version"
+    kapt "com.google.dagger:dagger-compiler:$dagger_version"
+    kapt "com.google.dagger:dagger-android-processor:$dagger_version"
}

If you use Butter Knife, you should also change to kapt, otherwise the views which are injected might be null.

2018-08-27 Weiyi Li