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

Flutter Clean架构:UI层复用Domain实体避免Bloc重复参数

解决Flutter Clean架构Presentation层参数重复问题

1. 优先复用Domain层的Order实体

直接用Domain层的Order实体替代零散参数,是最直接减少样板代码的方式:

  • 把AddNewOrderMoveToSecondPage事件和AddNewOrderMoveToSecondPagePermitted状态里的orderType、orderTitle等参数,换成单个Order对象(建议用equatable或freezed实现不可变类)
  • 页面跳转时,直接传递整个Order对象作为路由参数,不用逐个字段传递
  • 注意:确保Order实体支持跨页面传递,比如用Navigator的arguments时,实体需要可序列化(可手动实现toJson/fromJson,或用freezed自动生成)

2. 按需创建Presentation层专用的草稿对象

如果Domain层的Order字段过多,或者需要添加UI专属的临时状态字段,可以创建一个OrderDraft类:

  • 只包含第一页需要的通用字段(orderType、orderTitle等),做成不可变类
  • Bloc的事件、状态都用OrderDraft传递数据,页面间跳转也直接传这个对象
  • 第二页补充完信息后,再把OrderDraft转换成Domain层的Order实体,调用新增订单用例
  • 好处:贴合UI流程,避免携带无关字段,保持Presentation层的独立性

3. 代码改造示例

Bloc事件与状态改造

// 改造后的事件
class AddNewOrderMoveToSecondPage extends AddNewOrderEvent {
  final OrderDraft orderDraft; // 或者Domain层的Order

  AddNewOrderMoveToSecondPage(this.orderDraft);
}

// 改造后的状态
class AddNewOrderMoveToSecondPagePermitted extends AddNewOrderState {
  final OrderDraft orderDraft;

  AddNewOrderMoveToSecondPagePermitted(this.orderDraft);
}

页面跳转逻辑

BlocListener<AddNewOrderBloc, AddNewOrderState>(
  listener: (context, state) {
    if (state is AddNewOrderMoveToSecondPagePermitted) {
      Navigator.push(
        context,
        MaterialPageRoute(
          builder: (context) => SecondOrderPage(draft: state.orderDraft),
        ),
      );
    }
  },
)

4. Clean架构下的关键注意点

  • 复用Domain实体时,Presentation层只能读取字段,不能直接修改实体(实体必须是不可变的),修改操作要通过Bloc发送事件更新状态
  • 如果用Presentation层的OrderDraft,转换为Domain层Order的逻辑要放在Presentation层的mapper类里,绝对不能让Domain层依赖Presentation层
  • 用equatable或freezed处理实体/状态的相等性,避免Bloc触发不必要的状态更新

内容的提问来源于stack exchange,提问作者Lemon Grab

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.16 02:05:05