如何使用 Android Room 正确获取 DAO 类中的表名称

wap*_*apn 6 android kotlin android-room

我想知道在 Android Room 查询中使用表名时如何避免硬编码。我用 开发Kotlin,但说实话,在这个问题上,使用 Java 还是 Kotlin 并不重要。

让我们看看简单的类:

DAO接口:

@Dao
interface UserDAO {

    @Query("SELECT * FROM USER")
    fun getAll(): List<User>
}
Run Code Online (Sandbox Code Playgroud)

实体类:

@Entity(tableName = "USER")
class User {
}
Run Code Online (Sandbox Code Playgroud)

可以看到表名“USER”被硬编码在UserDAO中的@Query中。如何避免这种情况?如何引用@Entity参数tableName

我希望将所有名称集中在一处。

小智 8

您可以在任何 Util 类中创建常量,并可以在 Entity 和 Dao 类中引用该变量,如下所示:-

假设在 MainActivity 中你有

    companion object {
        const val TABLE_NAME: String="Cheese"
    }
Run Code Online (Sandbox Code Playgroud)

实体类

@Entity(tableName = MainActivity.TABLE_NAME)
Run Code Online (Sandbox Code Playgroud)

Dao 类将是

@Query("SELECT * FROM "+MainActivity.TABLE_NAME)
Run Code Online (Sandbox Code Playgroud)

注意:-这是避免硬编码命名的常用方法,您可以从实体类中获取表名(需要探索):)。

  • 这个答案是正确的,但值得注意的是,数据库中的每个表都应该有单独的带有常量的类。另外,常量类的名称应该引用数据库表的名称。应避免将常量名称放在“MainActivity”类中。 (2认同)

gar*_*707 6

目前,对于 Kotlin 和 Java,您都可以依赖内置的 SQL 语法高亮显示。因此,当您键入查询内容时,Android Studio 会建议已定义的表名称。也许您已经以某种方式关闭了该功能? 不要忘记注入 Android Room SQL 语言

总而言之,如果您希望保留硬编码的内容,为什么不定义属于Entity类的伴生对象呢?恕我直言,混合数据(层)和活动类不是一个好概念。数据不知道诸如活动之类的东西(或任何与 UI 相关的东西)。拥有Utils听起来就像所有事情都有一个错误,而不是从关注点的角度来看。

也许下面的代码可以满足您的要求:

@Entity(tableName = WordPl.TABLE_NAME)
data class WordPl(var id: Int,                      
                  var word: String) {

    companion object {
        const val TABLE_NAME = "word_pl"
    }

}
Run Code Online (Sandbox Code Playgroud)

然后在您的 DAO 中,您可以使用 Kotlin 字符串模板:

@Dao
interface DictionaryDao {

    @Query("Select * from ${WordPl.TABLE_NAME}")
    fun getAllWords(): List<WordPl>

}
Run Code Online (Sandbox Code Playgroud)