Что такое mapDispatchToProps?
Я читал документацию для библиотеки Redux, и у нее есть этот пример,
в дополнение к чтению состояния, компоненты контейнера могут отправлять действия. Аналогичным образом можно определить функцию
mapDispatchToProps()
который получает метод dispatch () и возвращает реквизит обратного вызова, который вы хотите ввести в презентационный компонент.
это на самом деле не имеет смысла. Зачем вам нужно mapDispatchToProps
когда у вас уже есть mapStateToProps
?
они также обеспечивают этот удобный пример кода:
const mapDispatchToProps = (dispatch) => {
return {
onTodoClick: (id) => {
dispatch(toggleTodo(id))
}
}
}
может кто-нибудь объяснить в терминах непрофессионалов, что это за функция и почему она полезна?
5 ответов
я чувствую, что ни один из ответов кристаллизуется, почему mapDispatchToProps
полезно.
на это действительно можно ответить только в контексте container-component
шаблон, который я нашел наиболее понятным при первом чтении:
https://medium.com/@learnreact/container-components-c0e67432e005#.1a9j3w1jl
затем
http://redux.js.org/docs/basics/UsageWithReact.html
в двух словах, ваша components
предполагается, что они должны заниматься только показом вещей. The единственное место, откуда они должны получать информацию, - это их реквизит.
отделено от "отображения материала" (компонентов):
- как вы получаете материал для отображения,
- и как вы обрабатываете события.
что это containers
для.
следовательно, "хорошо спроектированный"component
в шаблоне выглядят как это:
class FancyAlerter extends Component {
sendAlert = () => {
this.props.sendTheAlert()
}
render() {
<div>
<h1>Today's Fancy Alert is {this.props.fancyInfo}</h1>
<Button onClick={sendAlert}/>
</div>
}
}
посмотрите, как этот компонент получает информацию, которую он отображает из реквизита (который пришел из магазина redux через mapStateToProps
) и он также получает свою функцию действия от своих реквизитов:sendTheAlert()
.
вот тут mapDispatchToProps
входит: в соответствующем container
// FancyButtonContainer.js
function mapDispatchToProps(dispatch) {
return({
sendTheAlert: () => {dispatch(ALERT_ACTION)}
})
}
function mapStateToProps(state} {
return({fancyInfo: "Fancy this:" + state.currentFunnyString})
}
export const FancyButtonContainer = connect(
mapStateToProps, mapDispatchToProps)(
FancyAlerter
)
интересно, видите ли вы, теперь, когда это container
[1] что знает о redux и отправки и хранения и государства и ... материал.
на component
in узор,FancyAlerter
, который делает рендеринг не должен знать ни о каком из этих вещей: он получает свой метод для вызова в onClick
кнопки, через его реквизит.
и ... mapDispatchToProps
Было полезным средством, которое redux предоставляет, чтобы позволить контейнеру легко передать эту функцию в обернутый компонент на его реквизитах.
все это очень похоже на пример todo в docs, и еще один ответ здесь, но я попытался бросить его в свете шаблона, чтобы подчеркнуть почему.
(Примечание: Вы не можете использовать mapStateToProps
С той же целью, что и mapDispatchToProps
по основной причине, что у вас нет доступа к dispatch
внутри mapStateToProp
. Так что вы не могли использовать mapStateToProps
чтобы дать обернутому компоненту метод, который использует dispatch
.
я не знаю, почему они решили разбить его на две картографические функции - возможно, было бы аккуратнее иметь mapToProps(state, dispatch, props)
IE одна функция, чтобы сделать оба!
[1] Обратите внимание, что I намеренно явно названный контейнер FancyButtonContainer
, чтобы подчеркнуть, что это" вещь " - идентичность (и, следовательно, существование!) контейнера как "вещи" иногда теряется в стенографии
export default connect(...)
синтаксис, который показан в большинстве примеров
это в основном стенография. Поэтому вместо того, чтобы писать:
this.props.dispatch(toggleTodo(id));
вы бы использовали mapDispatchToProps, как показано в вашем примере кода, а затем в другом месте напишите:
this.props.onTodoClick(id);
или, скорее всего, в этом случае у вас будет это как обработчик событий:
<MyComponent onClick={this.props.onTodoClick} />
здесь есть полезное видео Дэна Абрамова: https://egghead.io/lessons/javascript-redux-generating-containers-with-connect-from-react-redux-visibletodolist
mapStateToProps()
это утилита, которая помогает вашему компоненту получить обновленное состояние (которое обновляется некоторыми другими компонентами),mapDispatchToProps()
- это утилита, которая поможет вашему компоненту запустить событие действия (диспетчерское действие, которое может вызвать изменение состояния приложения)
mapStateToProps
, mapDispatchToProps
и connect
С react-redux
библиотека предоставляет удобный способ доступа к вашим state
и dispatch
функция вашего магазина. Поэтому в основном connect-это компонент более высокого порядка, вы также можете использовать его как обертку, если это имеет смысл для вас. Так что каждый раз ваш state
изменить mapStateToProps
будет вызван с вашим новым state
и впоследствии, как вы props
update component запустит функцию рендеринга для рендеринга вашего компонента в браузере. mapDispatchToProps
также хранит ключ-значение the props
компонента, как правило, они принимают форму функции. Таким образом, вы можете вызвать state
изменение от вашего компонента onClick
, onChange
событий.
из docs:
const TodoListComponent = ({ todos, onTodoClick }) => (
<ul>
{todos.map(todo =>
<Todo
key={todo.id}
{...todo}
onClick={() => onTodoClick(todo.id)}
/>
)}
</ul>
)
const mapStateToProps = (state) => {
return {
todos: getVisibleTodos(state.todos, state.visibilityFilter)
}
}
const mapDispatchToProps = (dispatch) => {
return {
onTodoClick: (id) => {
dispatch(toggleTodo(id))
}
}
}
function toggleTodo(index) {
return { type: TOGGLE_TODO, index }
}
const TodoList = connect(
mapStateToProps,
mapDispatchToProps
)(TodoList)
также убедитесь, что вы знакомы с реагировать функции без гражданства и Компоненты Более Высокого Порядка
mapStateToProps
получает state
и props
и позволяет извлекать реквизит из состояния для передачи компоненту.
mapDispatchToProps
получает dispatch
и props
и предназначен для привязки создателей действий к отправке, поэтому при выполнении результирующей функции действие отправляется.
Я считаю, это только избавляет вас от необходимости делать dispatch(actionCreator())
внутри вашего компонента, что делает его немного проще читать.
https://github.com/reactjs/react-redux/blob/master/docs/api.md#arguments