Reputation: 1191
My instinct tells me no, but I'm having difficultly thinking of a better way.
Currently, I have a component that displays a list of items. Depending on the provided props
, this list may change (i.e. filtering change or contextual change)
For example, given a new this.props.type
, the state will be updated as follows:
componentWillReceiveProps(nextProps) {
if (nextProps.type == this.state.filters.type) return
this.setState({
filters: {
...this.state.filters,
type: nextProps.type,
},
items: ItemsStore.getItems().filter(item => item.type == nextProps.type)
})
}
This is all fine and good, but now my requirements have changed and I need to add a new filter. For the new filter, I must execute an API call to return a list of valid item ids and I only want to display items with these ids in the same list component. How should I go about this?
I had thought about calling the appropriate action from componentWillReceiveProps
, but that doesn't seem right.
componentWillReceiveProps(nextProps) {
if (nextProps.type == this.state.filters.type && nextProps.otherFilter == this.state.filters.otherFilter) return
if (nextProps.otherFilter != this.state.filters.otherFilter) {
ItemsActions.getValidIdsForOtherFilter(nextProps.otherFilter)
// items will be properly updated in store change listener, onStoreChange below
}
this.setState({
filters: {
...this.state.filters,
type: nextProps.type,
otherFilter: nextProps.otherFilter,
},
items: ItemsStore.getItems().filter(item => item.type == nextProps.type)
})
},
onStoreChange() {
let validIds = ItemsStore.getValidIds()
this.setState({
items: ItemsStore.getItems().filter(item => item.type == this.state.filters.type && validIds.indexOf(item.id) > -1)
})
}
Upvotes: 3
Views: 4567
Reputation: 5902
Update 22nd January 2018:
Recently an RFC-PR for React was merged, which deprecates componentWillReceiveProps
as it can be unsave when used in the upcoming async rendering mode. An example for this can be calling flux actions from this lifecycle hook.
The correct place to call actions (i.e. side effects) is after React is done rendering, so that means either componentDidMount
or componentDidUpdate
.
If the intention of the action is to fetch data, React might support a new strategy for these things in the future. In the meantime it's safe to stick to the two mentioned lifecycle hooks.
Upvotes: 10