Typescript 使用redux设置嵌套在不可变映射中的属性的值
我正在尝试使用减缩器设置Typescript 使用redux设置嵌套在不可变映射中的属性的值,typescript,redux,immutable.js,Typescript,Redux,Immutable.js,我正在尝试使用减缩器设置state.case.summaries.get(action.summary.id).metadata.summaryRank的值摘要isImmutable.Map 我试过这个: return { ...state, 'case' : { ...state.case, summaries : { ...s
state.case.summaries.get(action.summary.id).metadata.summaryRank
的值<代码>摘要isImmutable.Map代码>
我试过这个:
return {
...state,
'case' : {
...state.case,
summaries : {
...state.case.summaries,
[action.summary.id] : {
...state.case.summaries.get(action.summary.id),
metadata : {
...state.case.summaries.get(action.summary.id).metadata,
summaryRank : action.newRank
}
}
}
}
};
但我正在失去我的类型:
`state` before:
ApplicationState {_map: Map, __ownerID: undefined}
after:
{_map: Map, __ownerID: undefined, case: {…}}
`case` before:
Case {_map: Map, __ownerID: undefined}
after:
{_map: Map, __ownerID: undefined, summaries: {…}}
`summaries` before
Map {size: 44, _root: HashArrayMapNode, __ownerID: undefined, __hash: undefined, __altered: false}
after
{size: 44, _root: HashArrayMapNode, __ownerID: undefined, __hash: undefined, __altered: false, …}
因此,如果我以后尝试执行summaries.get(summaryId)
,我最终得到的结果是applicationState.case.summaries.get不是一个函数
然后我试着这样做:
return state.set('case',
state.case.set('summaries',
state.case.summaries.get(action.summary.id).set(//not sure what to do here
state.case.summaries.get(action.summary.id).set('metadata',
state.case.summaries.get(action.summary.id).metadata.set('summaryRank',
action.newRank
)
)
)
)
);
但我得到了:
[exec]
[exec] 46 state.case.summaries.get(action.summary.id).set(
[exec] ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
[exec] 47 state.case.summaries.get(action.summary.id).set('metadata',
[exec] ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
[exec] ...
[exec] 51 )
[exec] ~~~~~~~~~~~~~~~~~~~~~~~~~
[exec] 52 )
[exec] ~~~~~~~~~~~~~~~~~~~~~
[exec]
[exec] .../services/store/caseReducer.ts(46,21): error TS2346: Supplied parameters do not match any signature of call target.
[exec]
更多信息
case.ts
const CaseRecord = Immutable.Record({
id: '',
reserved:false,
loaded: false,
summaries: Immutable.Map<string, Summary>(),
caseMetadata: new models.CaseMetadata(),
});
export class Case extends CaseRecord {
public id: string;
public loaded: boolean;
public reserved: boolean;
public summaries: Immutable.Map<string, Summary>;
public caseMetadata: models.CaseMetadata;
constructor(properties?: any) {
super(properties);
}
public asMutable(): Case {
let record = <Case>super.asMutable();
record.summaries = this.summaries.asMutable();
this.summaries.forEach((summary) => {
record.summaries = record.summaries.set(summary.id, <models.Summary>summary.asMutable());
});
record.caseMetadata = this.caseMetadata.asMutable();
return record;
}
}
在redux存储中使用类类型时要小心——必须确保没有使用普通的JS对象
当您执行以下操作时:
return { /* stuff */ }
return Object.assign(new ApplicationState(), { /* stuff */ })
redux无法判断您是从另一种类型派生出来的。您可以通过以下方式应用原始原型:
return { /* stuff */ }
return Object.assign(new ApplicationState(), { /* stuff */ })
然而,当有大量的筑巢时,这是相当乏味的
谢天谢地,您似乎一直在使用不可变的东西,这使得更新嵌套类型相当容易。我相信你可以做到:
return state.setIn(
['case', 'summaries', action.summary.id, 'metadata', 'summaryRank'],
action.newRank
)
这将根据需要创建键,并根据需要使用Immutable的映射。由于我没有看到ApplicationState和Case类,所以有点难以确定发生了什么。有什么理由让它们成为类,而不是一路使用Immutable.js映射吗?@KevinRaoofi-我已经在上面添加了这些类。这些类的可能重复实现了这个目的,并且比我预期的要干净得多。谢谢