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

Flutter更新Firebase用户集合Article列表时触发ArgumentError错误

问题描述

尝试更新Firebase用户集合中类型为Article列表的savedArticles字段,添加新Article后更新收藏文章页面,但调用saveArticleToReadingList函数时触发错误:ArgumentError (Invalid argument: Instance of 'Article'),此前未找到有效解决方案。

AmataUser模型

@JsonSerializable()
class AmataUser {
  String? userName;
  String? emailAddrress;
  String? uid;
  String? profileUrl;
  List<Article>? savedArticles;

  AmataUser(
      {this.emailAddrress, this.profileUrl, this.savedArticles, this.userName, this.uid});

  factory AmataUser.fromJson(Map<String, dynamic> json) =>
      _$AmataUserFromJson(json);

  Map<String, dynamic> toJson() => _$AmataUserToJson(this);

  AmataUser copyWith(
          {String? emailAddres,
          String? password,
          String? profileUrlm,
          List<Article>? savedArticles}) =>
      AmataUser(
          profileUrl: profileUrl ?? this.profileUrl,
          emailAddrress: emailAddrress ?? this.emailAddrress,
          savedArticles: savedArticles ?? this.savedArticles);
}

Article模型

@JsonSerializable()
class Article {
  String? title;
  String? body;
  String? coverImageUrl;
  Article({this.body, this.coverImageUrl, this.title});

  factory Article.fromJson(Map<String, dynamic> json) =>
      _$ArticleFromJson(json);

  Map<String, dynamic> toJson() => _$ArticleToJson(this);

  Article copyWith({String? title, String? body, String? coverImageUrl}) {
    return Article(
      title: title??this.title,
      body: body??this.body, 
      coverImageUrl:coverImageUrl??this.coverImageUrl
    );
  }
}

更新函数(原代码)

Future<RawData> saveArticleToReadingList(
    {required AmataUser user, required Article article}) async {
  try {
    log('saving ${article.title} to user list');
    var doc = await _userRef.doc(user.uid).get();
    AmataUser amatauser = AmataUser.fromJson(doc.data() as Map<String, dynamic>);
    amatauser.savedArticles!.add(article);
    print(amatauser.savedArticles!.length);
    var resualt = await _userRef
        .doc(user.uid)
        .update({'savedArticles': amatauser.savedArticles});
    return RawData();
  } catch (e) {
    return RawData(operationResult: OperationResult.fail, data: e.toString());
  }
}

问题原因与修复方案

原因

Firebase Firestore无法直接存储Dart自定义对象(如Article实例),仅支持可序列化的基础类型或Map<String, dynamic>结构。原代码直接传入List<Article>到update方法,导致类型不匹配触发错误。

修复步骤

  1. 初始化空列表:避免savedArticles为null时调用add方法触发空指针异常;
  2. 转换对象为Map结构:将列表中每个Article实例通过toJson()方法转为Map<String, dynamic>,再传入Firebase更新方法。

修复后的更新函数:

Future<RawData> saveArticleToReadingList(
    {required AmataUser user, required Article article}) async {
  try {
    log('saving ${article.title} to user list');
    var doc = await _userRef.doc(user.uid).get();
    AmataUser amatauser = AmataUser.fromJson(doc.data() as Map<String, dynamic>);
    
    // 初始化空列表,避免null调用add
    amatauser.savedArticles ??= [];
    amatauser.savedArticles!.add(article);
    
    print(amatauser.savedArticles!.length);
    var result = await _userRef
        .doc(user.uid)
        // 将Article列表转为Map列表
        .update({'savedArticles': amatauser.savedArticles!.map((art) => art.toJson()).toList()});
    return RawData();
  } catch (e) {
    return RawData(operationResult: OperationResult.fail, data: e.toString());
  }
}

内容的提问来源于stack exchange,提问作者Abolfazl Mashhadi

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.19 15:55:17