Как заявление об отказе от ответственности, это не "всегда" так, но в большинстве случаев документы пытаются указать вам правильное направление.
Поскольку повторный выбор запоминает возвращаемый результат селекторов, возвращаяизменчивый объект оставляет вас восприимчивым к хитрым ошибкам.Представьте себе следующий сценарий:
// Immutable State
{
todos: [{ text: "hey"}, { todo: "text"}]
}
// Selectors
const getTodos = createSelector(state => state.todos, immutableTodos => immutableTodos.toJS())
Селектор getTodos
возвращает простой объект JS, который по умолчанию является изменяемым.Теперь представьте несколько интеллектуальных компонентов, которые используют селектор getTodos
.
class EditTodos extends PureComponent {
constructor(props) {
this.state = { todos: props.todos }
}
addUnsavedTodo(newTodo) {
// Accidentally mutate the return result of getTodos
const newTodos = this.state.todos.push(newTodo)
this.setState({ todos: newTodos })
}
render() { // Some components for adding unsaved todos }
}
const mapStateToProps = (state) => ({ todos: getTodos(state))
Второй компонент, также использующий getTodos
, увидит новый «несохраненный» todo, как только будет вызван addUnsavedTodo
, что, скорее всего, будет непреднамеренным.Все вызовы getTodos
, при условии, что приставка state
не изменилась, получат одинаковую ссылку, и любые мутации коснутся всех потребителей.
Приведенный выше пример надуман, но, надеюсь, он демонстрирует одну из причин, по которой возвращение простых объектов JS может быть рискованным.
Кроме того, поскольку в документах упоминается , вам следуетограничьте использование toJS
, поскольку оно влияет на производительность.Преобразование вашего неизменного объекта в простой JS-объект в селекторе не имеет смысла