首页 / 资讯中心 / 文章详情

Fish Redux OnError 详解:Effect 业务异常的统一捕获与集中处理机制

Fish Redux OnError 详解:Effect 业务异常的统一捕获与集中处理机制 ★ FEATURED ARTICLE
前端【免费下载链接】fish-reduxAn assembled flutter application framework.项目地址https://gitcode.com/gh_mirrors/fi/fish-redux点击查看免费下载导读onError是 Fish Redux 为Component/Page提供的异常处理回调用于集中捕获由 Effect 产生的业务异常——无论异常来自同步 Effect 还是异步 Effect都会被统一送入同一个处理器。本文以 on-error-cn.md 为骨架结合 Component 构造函数 的参数签名、Effect 派发链路 以及仓库测试示例讲解onError的签名、语义、判定规则与真实用法并顺带说明它与 View 层兜底中间件的分工边界帮助你理解站在更高抽象层面简化业务代码这一设计意图。一、为什么需要统一的 onError在 Fish Redux 的组件模型中业务逻辑被拆解为 Reducer纯函数状态变更与 Effect副作用如网络请求、本地 IO、事件回调。Effect 中天然会产生异常同步函数里throw出来的异常、异步函数Future中抛出的错误都可能发生在业务代码的任意角落。如果没有统一的异常处理机制常见的做法是在每个 Effect 分支里各自try/catchif (action.type Action.load) { try { final data await api.fetch(); ctx.dispatch(ActionCreator.onData(data)); } catch (e) { // 每个分支都要自己处理一遍 showToast(load failed); } }当页面分支一多这段样板代码就会反复出现且每个分支的容错策略很容易写得五花八门。Fish Redux 给出的答案是在组件构造时提供一个onError回调让框架统一捕获 Effect 产生的业务异常集中决策哪些异常需要提示用户、哪些异常可以被静默吸收从而把异常策略从业务分支中抽离出来站在更高抽象角度对业务代码做合理简化。从源码结构看LogicTlogic.dart把组件逻辑封装为四部分——Reducer、Effect、Dependencies、Key其中 Effect 的创建与派发由框架接管createEffectDispatch、createNextDispatch、createDispatch见 helper.dart这为框架级统一捕获异常提供了天然的挂载点。二、onError 的签名与语义onError在ComponentT构造函数中以命名参数形式接收component.dart典型写法如下bool onMessageError(Exception e, ContextString ctx) { if (e is BizException) { /// do some toast return true; } return false; } class MessageComponent extends ComponentString { MessageComponent() : super( view: buildMessageView, effect: buildEffect(), reducer: buildMessageReducer(), onError: onMessageError, ); }要点拆解要素说明回调签名bool Function(Exception e, ContextT ctx)参数e被捕获到的异常对象通常是 Effect 中抛出的具体异常实例参数ctx抛出异常时所在的组件ContextT可用于读取ctx.state、ctx.dispatch继续下发 Action返回值bool中断标记返回true表示该异常已被处理、拦截interrupt返回false表示异常未被本处理器处理交由链路继续按默认规则放行传入位置Component、Page构造函数的命名参数onErrorbool返回值的中断interrupt语义与 Fish Redux 的 Effect 约定一脉相承在 basic.dart 中EffectT的类型注释明确写着Interrupt if not null not false返回非 null 且非 false 即视为中断同步函数用bool表达中断异步函数则用Futurevoid表示应始终被中断。onError的true/false正是沿用同一套判定习惯——true意味着我认识这个异常已处理不要再往下冒泡。从类型上还应注意由于ComponentT的 State 泛型不同ContextT的类型参数会随组件变化。例如仓库测试示例中 ToDoList 页面的处理器签名是bool toDoListErrorHandler(Exception exception, ContextToDoList ctx)test_widgets/lib/page/page.dart与ContextString的MessageComponent并不相同编写时需与具体组件 State 类型保持一致。三、捕获范围同步 Effect 与异步 Effect原文档强调onError集中处理由 Effect 产生的业务异常无论是同步函数还是异步函数。这一点可以从 Effect 的派发实现中得到印证在 helper.dart 中createEffectDispatch直接调用用户 Effect 并透传返回值Dispatch createEffectDispatchT(EffectT userEffect, ContextT ctx) { return (Action action) { final Object result userEffect?.call(action, ctx); // ... return result; }; }同步 EffectuserEffect?.call(action, ctx)在派发线程内执行throw的异常会沿调用栈被上层捕获进入onError异步 Effect当 Effect 返回Future如toDoListEffectAsync用Future.delayed包一层后执行见 test_widgets/lib/page/page.dart异步任务中抛出的错误同样会被框架统一收口到onError。也就是说只要异常来源是 Effect无论同步异步组件无需感知异常发生的位置与时机统一交给onError决策即可。同步与异步的细微差别根据 basic.dart 的注释约定Effect 本身也区分同步/异步中断语义同步 Effect返回booltrue表示中断后续不再执行 nextDispatch异步 Effect返回Futurevoid语义上应始终被中断。而onError回调始终是同步的bool函数它在异常发生的当下被调用返回true即吞掉该异常例如只弹 toast返回false则继续走框架默认的放行/兜底逻辑。测试示例 page_test.dart 中通过instrumentErrorToDoList(toDoListErrorHandler, ...)包装onError来插桩断言异常被捕获也印证了onError是 Effect 异常处理的统一入口。四、配合分支异常的实战模式已知异常与未知异常仓库测试代码test_widgets/lib/page/给出了一个非常典型的实战模式在 Effect 中按 Action 类型throw不同类型的异常在onError中按异常类型分类处理。Effect 侧page.dartbool toDoListEffect(Action action, ContextToDoList ctx) { if (action.type ToDoListAction.onKnowException) { throw KnowException(); // 已知异常业务可识别 } else if (action.type ToDoListAction.onUnKnowException) { throw UnKnowException(); // 未知异常不认识的错误 } return false; }异常类型定义exception.dartclass KnowException implements Exception { // 自定义 便于按类型比较 } class UnKnowException implements Exception { // ... }onError 侧page.dartbool toDoListErrorHandler(Exception exception, ContextToDoList ctx) { print(onErr:$exception); if (exception is KnowException) { return true; // 已知异常已处理如 toast拦截 } return false; // 未知异常不处理继续放行 }这种Effect 只管throwonError 统一分类的写法正是原文档所说站在更高抽象角度对业务代码做合理简化的直接体现Effect 内无需任何try/catch专注业务主流程已知异常如BizException、KnowException在onError中集中提示用户并返回true拦截未知异常返回false放行交由链路后续处理或由上层中间件兜底不会让未预期错误悄悄淹没。五、onError 与 View 层兜底中间件的分工需要澄清一个容易混淆的边界onError只负责 Effect 产生的业务异常View 层的渲染异常并不走它。仓库源码中另有一组safety*中间件用于 View/Adapter 渲染兜底safetyViewsafety_view.dart包装ViewBuilder在 build 抛出异常时调用用户提供的onError注意此处onError是中间件参数签名带StackTrace、component、store未提供回调时降级为Container(width: 0, height: 0)safetyAdaptersafety_adapter.dart包装AdapterBuilder区分构建 ListAdapter 阶段与逐 item 构建阶段两处 try/catch异常时同样回调onError或返回空容器/空列表。两个safety*中间件内部都有isDebug()判断调试模式下直接放行原始逻辑异常立即暴露仅发布/非调试构建下才启用兜底。这与onError的定位形成互补异常来源处理入口典型场景Effect 同步/异步业务异常组件onError回调网络失败、业务校验失败、已知/未知异常分类View build 阶段异常safetyView中间件渲染逻辑抛错避免白屏Adapter item 构建异常safetyAdapter中间件列表单项渲染异常避免整表崩溃从命名和传参看两套机制互不干扰组件的onError接收(Exception e, ContextT ctx)而中间件的onError接收(dynamic e, StackTrace st, {component, store})并返回一个兜底Widget。设计目标是让业务错误与渲染错误各归其位。六、接入方式与验证路径1. 在 Component 中接入如前文示例在ComponentT构造函数中传入onError命名参数即可。PageT, P继承自ComponentTpage.dart因此 Page 构造同样支持onError构造参数透传见 page.dart。当某个组件/页面没有自定义onError时Effect 异常将不被拦截沿派发链路按默认语义继续放行。2. 在测试中验证仓库的 ToDoList 测试工程把点击 Error 按钮 → Effect 抛 KnowException → onError 捕获串成一条可观察链路view 中点击Error按钮派发onKnowExceptionpage.dartEffect 抛异常toDoListErrorHandler打印onErr:$exception并返回true。虽然onError在实际用例中默认被注释page.dart但配合 page_test.dart 中被注释的instrumentError插桩写法可以清晰还原用包装函数包裹 onError 以断言异常是否被处理的测试思路。3. 边界与前提onError的参数类型ContextT与组件 State 泛型绑定跨组件复用处理器时需注意泛型匹配onError覆盖的是 Effect 异常Reducer 与 View 的异常处理分别依赖中间件体系不属于本机制职责范围返回true会拦截异常请确保该分支确实完成了对用户可见的处理如 toast、日志避免吞掉异常却不做任何反馈。总结Fish Redux 的onError以极小的 API 面一个bool回调为 Effect 的同步/异步业务异常提供了统一收口Effect 专注于抛onError 专注于分类与决策true拦截、false放行的中断语义与框架的 Effect 约定一脉相承。配合 helper.dart 的派发链路与 test_widgets/lib/page/page.dart 的已知/未知异常示例你可以轻松把异常策略从每个业务分支中剥离出来实现代码的集中简化。若需进一步了解 View/Adapter 渲染异常兜底可继续阅读 safety_view.dart 与 safety_adapter.dart。赞分享前端【免费下载链接】fish-reduxAn assembled flutter application framework.项目地址https://gitcode.com/gh_mirrors/fi/fish-redux点击查看免费下载相关推荐fish-redux OnError 机制解析统一处理 Effect 业务异常的抽象实践fish redux OnError 机制解析统一处理 Effect 业务异常的抽象实践 本篇技术指南聚焦 fish redux 框架中的 OnError 设前端h3 错误处理完全指南HTTPError、未处理异常与 onError 捕获机制h3 错误处理完全指南HTTPError、未处理异常与 onError 捕获机制 H3 会在 请求生命周期 https://link.gitcode.com/后端Web框架Fish Redux 的 Effect 机制详解副作用处理、异步请求与 Self-First-Broadcast 执行模型Fish Redux 的 Effect 机制详解副作用处理、异步请求与 Self First Broadcast 执行模型 本文围绕 Fish Redux 框前端创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考
阅读完成 · 觉得有帮助?
咨询建站