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

Flutter ObjectBox无法生成含自定义类的数据库模型问题

ObjectBox多实体关联构建报错解决方法

问题背景

跟随《NoSQL Database Storage | Flutter ObjectBox (vs Sqlite, Sqflite, Hive)》视频搭建多类ObjectBox数据库时,添加Set实体关联Exercise后,执行flutter pub run build_runner build出现两个报错:

  • Cannot use the default constructor of 'Set': don't know how to initialize param exercise - no such property.
  • [WARNING] objectbox_generator:resolver on lib/models/set.dart: skipping property 'exercise' in entity 'Set', as it has an unsupported type: 'Exercise?'

单独存在Exercise类时构建正常,添加关联属性后失败,尝试修改构造参数默认值和const构造未解决。

错误原因

ObjectBox不允许直接将实体类作为属性存储,必须通过**ToOne/ToMany关系注解**定义实体间的关联逻辑,直接用Exercise?作为属性不符合映射规则。

修改后的代码

Exercise.dart

import 'package:objectbox/objectbox.dart';
import 'set.dart';

@Entity()
@Sync()
class Exercise {
  int? id;
  final String? name;
  final String? target;
  final String? bodyPart;
  final String? equipment;
  final String? gifUrl;
  
  // 反向关联:一个Exercise对应多个Set
  final sets = ToMany<Set>();

  Exercise({
    this.id = 0,
    required this.name,
    required this.target,
    required this.bodyPart,
    required this.equipment,
    required this.gifUrl,
  });

  factory Exercise.fromJson(Map<String, dynamic> json) {
    return Exercise(
        id: int.tryParse(json['id'].toString()),
        name: json["name"].toString(),
        target: json["target"].toString(),
        bodyPart: json["bodyPart"].toString(),
        equipment: json["equipment"].toString(),
        gifUrl: json["gifUrl"].toString());
  }
}

Set.dart

import 'package:objectbox/objectbox.dart';
import 'exercise.dart';

@Entity()
@Sync()
class Set {
  int? id;
  final int? repetitions;
  
  // 关联Exercise的ToOne关系
  final exercise = ToOne<Exercise>();

  Set({
    this.id = 0,
    required Exercise exercise,
    required this.repetitions,
  }) {
    this.exercise.target = exercise;
  }
  
  // 可选:支持通过Exercise ID构造的工厂方法
  factory Set.withExerciseId({int? id, required int exerciseId, required int? repetitions}) {
    final set = Set(id: id, exercise: Exercise(name: "", target: "", bodyPart: "", equipment: "", gifUrl: ""), repetitions: repetitions);
    set.exercise.targetId = exerciseId;
    return set;
  }
}

关键修改说明

  1. Exercise类:添加ToMany<Set>类型的sets属性,用于管理该Exercise对应的所有Set实例,实现反向关联。
  2. Set类:用ToOne<Exercise>替代原Exercise?属性,通过target(传入实体对象)或targetId(传入实体ID)完成关联初始化。
  3. 构造函数中手动初始化关系属性,确保ObjectBox能正确识别关联逻辑。

重新构建命令

修改完成后执行以下命令生成模型:

flutter pub run build_runner build --delete-conflicting-outputs

内容的提问来源于stack exchange,提问作者Ali Haidar

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.22 00:36:28