如何从Firestore子集合获取数据?color字段返回null如何解决
问题修复方案
问题根因
- 类型不兼容:ProductColor类中的
color字段声明为Flutter原生Color类型,但Firestore中存储的是十六进制颜色字符串(如#FFFFFF),直接赋值无法完成类型转换,会触发异常导致整个colors对象返回null - 空校验缺失:调用
ProductColor.fromJson(json['color'])前未校验json['color']是否存在、是否为null,若数据库对应字段为空会直接返回null - (可选,根据数据库实际结构判断)若Firestore中color字段是多规格数组格式,你Product模型中声明的是单个
ProductColor对象,类型不匹配也会导致取值失败 - 额外无效代码:两处
json['']的取值逻辑使用空字符串作为key,必然返回null,建议同步修复
修复代码
修正后的ProductColor模型
class ProductColor { String id; Color color; String qty; String size; ProductColor({ this.id, this.color, this.qty, this.size, }); // 添加入参空校验,同时处理颜色字符串转Color逻辑 static ProductColor? fromJson(Map<String, dynamic>? json) { if (json == null) return null; // 处理十六进制颜色字符串转Color,适配带#和不带#的格式 String colorStr = json['color'] ?? '#FFFFFF'; if (colorStr.startsWith('#')) { colorStr = colorStr.substring(1); } Color finalColor = Color(int.parse('FF$colorStr', radix: 16)); return ProductColor( id: json['id'], // 替换为你实际的id字段key,不要用空字符串 color: finalColor, qty: json['qty'], size: json['size'], ); } Map<String, dynamic> toJson() => { 'id': id, // Color转十六进制字符串存库 'color': '#${color.value.toRadixString(16).substring(2).toUpperCase()}', 'qty': qty, 'size': size, }; }
修正后的Product模型fromJson逻辑
static Product fromJson(Map<String, dynamic> json) => Product( id: json['firestore_id'], title: json['productName'], description: json['productDescriptions'], category: json['categoryName'], images: json['image'], // 调用已加空校验的fromJson colors: ProductColor.fromJson(json['color']), // 修复空key问题,替换为你实际的rating字段key rating: json['rating']?.toDouble() ?? 0.0, price: json['price'], seller: Seller.froJson(json['seller']), approved: json['approved'], currency: json['priceCurrency'], condition: json['productCondition'], firestoreid: json['firestore_id'], );
补充说明
如果你的Firestore中color字段是数组类型(存储多个颜色规格),需要做如下调整:
- Product模型中colors字段改为
List<ProductColor>? colors; - fromJson中转换逻辑改为:
colors: (json['color'] as List?)?.map((e) => ProductColor.fromJson(e as Map<String, dynamic>)).toList(),
内容的提问来源于stack exchange,提问作者Oletech
相关产品推荐
相关产品推荐

