Вложенный интеллектуальный компонент React redux - состояние не отображается на реквизиты

Я создаю счетчик напитков, который будет подсчитывать количество выпитых напитков в рамках проекта по изучению Redux.

У меня есть начальное состояние, в котором есть свойство drink, которое содержит коллекцию напитков и их текущее количество:

//State

{
  drinks: {
    coffee: 0,
    water: 0,
  }
  //...
}

Я создал презентационный компонент Counter:

import React from 'react';
import PropTypes from 'prop-types';

import Button from './Button';

const ucFirst = string => string.charAt(0).toUpperCase() + string.slice(1);

const Counter = ({name, count, onIncrement, onDecrement}) => (
	<div className = "counter">
		<h2>{ucFirst(name)}</h2>
		<span>{count}</span>
		<Button onClick = {() => {onIncrement(name)}}>+</Button>
		<Button onClick = {() => {onDecrement(name)}}>-</Button>
	</div>
);

Counter.propTypes = {
	name: PropTypes.string.isRequired,
	count: PropTypes.number.isRequired,
	onIncrement: PropTypes.func.isRequired,
	onDecrement: PropTypes.func.isRequired,
}

export default Counter;

За ним следует компонент контейнера DrinkCounter:

import { connect } from 'react-redux'
import { incrementDrink, decrementDrink } from '../actions'
import Counter from '../components/Counter'

const mapStateToProps = (state, ownProps) => ({
	count: state.drinks[ownProps.drink],
	name: ownProps.drink
})

const mapDispatchToProps = dispatch => ({
	onIncrement: drink => dispatch(incrementDrink(drink)),
	onDecrement: drink => dispatch(decrementDrink(drink))
})

export default connect(
	mapStateToProps,
	mapDispatchToProps
)(Counter)

Это работает, как ожидалось, если я добавлю

<DrinksContainer name = "coffee" />

в мой компонент App.

Вот где начинается проблема. Я хочу создать еще два компонента: один презентационный и один контейнер, которые будут отображать ключи моего объекта drinks и выводить DrinkCounter для каждого. У меня есть следующий код, но я получаю сообщение об ошибке " Неудачный тип опоры: опора name помечена как обязательная в Counter, но ее значение - undefined "

Вот контейнер List:

import React, {Fragment} from 'react'
import PropTypes from 'prop-types'
import DrinkCounter from '../containers/DrinkCounter'

const List = ({drinks}) => {
  return (
	<Fragment>
	  {
			Object.keys(drinks).map(
				(drink, index) => (<DrinkCounter name = {drink} key = {index} />)
			)
		}
	</Fragment>
  )
}

List.propTypes = {
	drinks: PropTypes.object.isRequired
}

export default List

а вот контейнер DrinksList:

import React from 'react';
import {connect} from 'react-redux';
import List from '../components/List';

const mapStateToProps = state => ({
	drinks: state.drinks	
})

export default connect(mapStateToProps)(List);

Может ли кто-нибудь объяснить, в чем я ошибаюсь?

похоже, что в вашем DrinkCounter вы используете компонент Counter, но вы не передаете ему свойство name.

dee zg 24.11.2018 15:22

Я знаю, но в компоненте List, где отображается карта, я добавляю опору name, как этот <DrinkCounter name = {drink} key = {index} />

mrmadhat 24.11.2018 15:29

как выглядит ваш компонент DrinkCounter?

dee zg 24.11.2018 15:34

Код компонента DrinkCounter находится в теле вопроса.

mrmadhat 24.11.2018 15:44

Ну не совсем. вы не показываете ничего, кроме его методов mapStateToProps и mapDispatchToProps. где остальное?

dee zg 24.11.2018 15:45

Кстати, вы экспортируете connect(Counter) из DrinkCounter. какая-то причина или опечатка?

dee zg 24.11.2018 15:48
DrinkCounter по умолчанию экспортирует connect(mapStateToProps, mapDispatchToProps)(Counter). connect возвращает функцию, которая при вызове с компонентом (в данном случае Counter) возвращает новый компонент, который является переданным компонентом с пропсами, заполненными из состояния. Поэтому, когда я звоню <DrinkCounter name = {drink} key = {index} />, он по сути то же, что и <Counter name = {drink} key = {index} count = {state.drinks[drink]} onIncrement = {incrementDispatchFn} onDecrement = {decrementDispatchFn} />.
mrmadhat 24.11.2018 21:29

В процессе ответа я осознал свою ошибку! Я передаю name в качестве опоры для DrinkCounter, хотя он должен быть drink

mrmadhat 24.11.2018 21:30
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
В JavaScript одним из самых запутанных понятий является поведение ключевого слова "this" в стрелочной и обычной функциях.
Концепция локализации и ее применение в приложениях React ⚡️
Концепция локализации и ее применение в приложениях React ⚡️
Локализация - это процесс адаптации приложения к различным языкам и культурным требованиям. Это позволяет пользователям получить опыт, соответствующий...
Улучшение производительности загрузки с помощью Google Tag Manager и атрибута Defer
Улучшение производительности загрузки с помощью Google Tag Manager и атрибута Defer
В настоящее время производительность загрузки веб-сайта имеет решающее значение не только для удобства пользователей, но и для ранжирования в...
Безумие обратных вызовов в javascript [JS]
Безумие обратных вызовов в javascript [JS]
Здравствуйте! Юный падаван 🚀. Присоединяйся ко мне, чтобы разобраться в одной из самых запутанных концепций, когда вы начинаете изучать мир...
Система управления парковками с использованием HTML, CSS и JavaScript
Система управления парковками с использованием HTML, CSS и JavaScript
Веб-сайт по управлению парковками был создан с использованием HTML, CSS и JavaScript. Это простой сайт, ничего вычурного. Основная цель -...
JavaScript Вопросы с множественным выбором и ответы
JavaScript Вопросы с множественным выбором и ответы
Если вы ищете платформу, которая предоставляет вам бесплатный тест JavaScript MCQ (Multiple Choice Questions With Answers) для оценки ваших знаний,...
0
8
53
1
Перейти к ответу Данный вопрос помечен как решенный

Ответы 1

Ответ принят как подходящий

Я выяснил проблему, в компоненте List я неправильно указываю опору для DrinkCounter. Я передаю name, хотя на самом деле это должен быть drink.

Другие вопросы по теме