You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何从Firebase Cloud Firestore获取准确布尔值而非数据类构造初始值

问题场景
  • 基于Kotlin开发Android应用,定义了数据类作为Firestore的文档映射模型,其中包含名为isGamePlayed的布尔字段,默认值设为false
  • Firestore数据库中对应文档的isGamePlayed字段实际存储值为true
  • 读取数据到RecyclerView Adapter后,其余字段均能正常获取数据库中的存储值,唯独该布尔字段始终返回false,和实际存储值不符
  • 核心Adapter代码如下:
class OneTwoAdapter(
    private val oneTwoGames: MutableList<Game>
) : RecyclerView.Adapter<OneTwoViewHolder>() {
    override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): OneTwoViewHolder {
        return OneTwoViewHolder(
            LayoutInflater.from(parent.context)
                .inflate(R.layout.one_two_games_layout, parent, false)
        )
    }

    override fun onBindViewHolder(holder: OneTwoViewHolder, position: Int) {
        val gameDetail = oneTwoGames[position]

        holder.awayTeamName.text = gameDetail.awayTeam
        holder.gameDate.text = gameDetail.gameDate
        holder.league.text = gameDetail.league
        holder.homeTeamName.text = gameDetail.homeTeam
        holder.kickOff.text = gameDetail.kickOff
        holder.outCome.text = gameDetail.outCome
        Glide.with(holder.itemView.context)
            .load(gameDetail.homeImageUrl)
            .into(holder.homeTeamImgUrl)
        Glide.with(holder.itemView.context)
            .load(gameDetail.awayImageUrl)
            .into(holder.awayTeamImgUrl)
        
        // 此处Toast输出始终为false,和数据库存储的true不符
        Toast.makeText(
            holder.itemView.context, "Status: ${gameDetail.isGamePlayed}",
            Toast.LENGTH_SHORT
        ).show()

        holder.game = gameDetail
    }

    override fun getItemCount(): Int {
        return oneTwoGames.size
    }
}
问题原因

这是Kotlin布尔属性生成规则和Firestore SDK默认映射逻辑的已知冲突:

  1. 按照Kotlin的类成员生成规则,以is为前缀命名的布尔属性,自动生成的getter方法名就是属性名本身(即isGamePlayed()),不会生成常规JavaBean规范的getIsGamePlayed()格式getter
  2. Firestore SDK反序列化做字段匹配时,会把is开头的getter方法名去掉前缀is,将剩余部分作为要匹配的Firestore字段名——也就是说,它会去Firestore文档里找名为gamePlayed的字段给isGamePlayed属性赋值,完全不会匹配你实际存储的isGamePlayed字段
  3. 因为匹配不到对应字段,SDK直接使用了你在数据类里给该属性设置的默认值false,其余字段没有is前缀带来的命名冲突,所以可以正常匹配到同名字段,读取到正确值。
修复方案

任选以下一种方案修改即可解决问题:

  • 方案1:用@PropertyName注解显式指定字段映射关系,强制SDK匹配Firestore中存储的isGamePlayed字段,示例写法:
    data class Game(
        // 其余字段保持原有定义不变
        @get:PropertyName("isGamePlayed")
        @set:PropertyName("isGamePlayed")
        val isGamePlayed: Boolean = false
    )
    
  • 方案2:统一两端字段命名,去掉属性名的is前缀,比如将数据类中的属性改名为gamePlayed,同时将Firestore中存储的对应字段名也修改为gamePlayed,保持命名完全一致即可正常映射。

内容的提问来源于stack exchange,提问作者Kevin Kyei

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.01 16:33:26