如何在NgRx reducer中修改Store特定属性并统一格式化日期字段
在NgRx Reducer中统一处理日期格式化的实现方式
直接在对应action的状态处理回调中调用格式化方法即可,reducer本身的职责就是将接口返回的原始数据转换为适合全局存储、可直接被组件消费的标准化状态,在这里做统一格式化完全符合NgRx的设计规范。
具体实现
首先在reducer文件中引入你封装好的reformatDateField工具方法,修改getVisitsListSuccess对应的状态处理逻辑,注意不要直接修改原始payload对象,要生成新的状态副本,遵守不可变数据原则:
// 引入格式化工具方法,替换为你项目中的实际路径 import { reformatDateField } from '@/utils/date'; const reducer = createReducer( initialState, on(fromActions.getVisitsListSuccess, (state, { payload }) => ({ ...state, // 拷贝原始payload后替换格式化后的日期字段 visits: { ...payload, createdAt: reformatDateField(payload.createdAt), lastUpdatedAt: reformatDateField(payload.lastUpdatedAt) } satisfies IVisit, })), on(fromActions.getVisitRedirectsListSuccess, (state, { payload }) => ({ ...state, redirects: payload, // 如果redirects字段中也包含需要格式化的日期,参照上面的逻辑处理即可 })), );
列表场景适配
从你的action命名getVisitsListSuccess判断,如果visits实际存储的是IVisit[]类型的数组而非单个对象,只需要通过map遍历处理每一项即可:
on(fromActions.getVisitsListSuccess, (state, { payload }) => ({ ...state, visits: payload.map((visitItem) => ({ ...visitItem, createdAt: reformatDateField(visitItem.createdAt), lastUpdatedAt: reformatDateField(visitItem.lastUpdatedAt) })) satisfies IVisit[], })),
注意事项
- 禁止直接修改传入的payload对象:比如不要直接写
payload.createdAt = reformatDateField(payload.createdAt),这会破坏NgRx的不可变数据要求,导致状态变更检测失效、数据污染等难以排查的问题 - 所有格式化逻辑统一收敛在reducer层后,组件从store中select取到的
visits数据已经是处理完成的格式,可以直接用于模板渲染,不需要在每个组件中重复调用格式化方法
内容的提问来源于stack exchange,提问作者ShadaMon
相关产品推荐
相关产品推荐

