代码之家  ›  专栏  ›  技术社区  ›  Mosius sMiLo

Android:使用Room和RxJava检查数据库中是否存在对象

  •  1
  • Mosius sMiLo  · 技术社区  · 6 年前

    Room 作为ORM,下面是我的Dao接口:

    @Dao
    interface UserDao {
        @Query(value = "SELECT * FROM User LIMIT 1")
        fun get(): Single<User?>
    
        @Insert(onConflict = OnConflictStrategy.REPLACE)
        fun add(profile: User)
    }
    

    另一方面,我在存储库中有一个方法可以检查用户是否登录,下面是实现代码:

    override fun isUserLogin(): Single<Boolean> = userDao
                .get().async()
                .onErrorReturn { null }
                .map { it != null }
    

    查询返回空结果集:SELECT*FROM User LIMIT 1

    我想回来 null 在本例中,但当我执行代码时,它会引发一个异常,消息如下:

    我不能用 Optional 因为道回来了 Single<User?> 所以 onErrorReturn 应该返回相同的类型。

    如何在不改变Dao的情况下检查用户是否存在?

    3 回复  |  直到 6 年前
        1
  •  7
  •   lelloman    6 年前

    COUNT

    @Query("SELECT COUNT(*) from User")
    fun usersCount() : Single<Int>
    

    它将返回表中的行数,如果为0,则表示数据库中没有用户,因此。

    override fun isUserLogin(): Single<Int> = userDao
                .usersCount()
                .async()
                .map { it > 0 }
    

    如果你真的想用丑陋的方式去做:

    @Query(value = "SELECT * FROM User LIMIT 1")
    fun get(): Single<User>
    

    不要使用可为null的类型,这是毫无意义的。然后映射到Boolean并处理异常:

    override fun isUserLogin(): Single<Boolean> = userDao
            .get()
            .async()
            .map { true }
            .onErrorReturn { false }
    
        2
  •  1
  •   Kiskae    6 年前

    使用 Maybe ,它准确地模拟了预期0个结果、1个结果或异常的响应。

        3
  •  0
  •   Chris    6 年前

    如果将DAO更改为返回一个可流动的用户列表,则可以通过检查列表的大小将其映射为布尔值。

    @Query(value = "SELECT * FROM User LIMIT 1")
    fun get(): Flowable<List<User>> 
    

    fun isUserLogin(): Single<Boolean> = userDao
        .get()
        .flatMapSingle { Single.just(it.size == 1) }
        .onErrorReturn { false }
        .first(false)