【问题标题】:props not being passed to components after implementing combineReducers in react-redux在 react-redux 中实现 combineReducers 后,道具未传递给组件
【发布时间】:2017-05-16 02:31:39
【问题描述】:

我正在尝试使用 react-redux 将道具传递给多个组件。我接收并尝试传递的数据来自数据库,因此涉及异步性。因为 props 在碰到组件时没有定义,所以我的应用程序抛出了一个未定义的错误。在组件中抛出错误后,它会继续解析状态,但是一旦定义了状态,它就不会使用新的 props 重新渲染组件。另一个掘金......我正在使用 combineReducers。在使用 combineReducers(仅使用婴儿减速器)之前,我没有这个问题。它是在我制作了另一个减速器并将其与 (baby-reducer) 组合之后开始的。知道这里发生了什么吗?为什么我的组件不会重新渲染?

这是我正在渲染组件的容器:

import React,{Component} from 'react'
import store from '../store'
import {connect} from 'react-redux';
import BabyProfile from '../components/BabyProfile'
import Weight from '../components/Weight'
import Height from '../components/Height'
import Feed from '../components/Feed'
import Sleep from '../components/Sleep'
import Diaper from '../components/Diaper'


class BabyProfileContainer extends Component {

  render(){
    // console.log("RENDER PROPS", this.props)
    const  {baby, weight, height, feed, sleep, diapers} = this.props

    return(
      <div>
        <BabyProfile baby={baby}/>
        <Weight weight={weight}/>
        <Height height={height}/>
        <Feed  feed={feed}/>
        <Sleep sleep={sleep}/>
        <Diaper diapers={diapers}/>
      </div>
    )
  }
}

const mapStateToProps = (state, ownProps) => {
  // console.log("MSTP Baby Container", state, "OWN PROPS", ownProps)
  return {
    baby: state.baby,
    diapers: state.diapers,
    weight: state.weight,
    height: state.height,
    sleep: state.sleep,
    feed: state.feeding
  }
}



export default connect(mapStateToProps)(BabyProfileContainer)

这是我的婴儿减速器:

import {RECEIVE_BABY} from '../constants'


const initialBabyState = {
  baby: {},
  diapers: [],
  weight: [],
  height: [],
  feeding: [],
  sleep: []

}

export default function(state = initialBabyState, action){
console.log('BABY REducer')

const newState = Object.assign({}, state)

   switch (action.type){

     case RECEIVE_BABY:
     newState.baby = action.baby;
     newState.diapers = action.diapers
     newState.weight = action.weight;
     newState.height = action.height;
     newState.feeding = action.feeding;
     newState.sleep = action.sleep

     break;




     default:
      return state

   }
   return newState

}

这是我的组合减速器:

import {combineReducers} from 'redux'
import baby from './baby-reducer'
import parent from './parent-reducer'



export default combineReducers({
  baby,
  parent

})

这是我的体重分量:

import React from 'react';
import {Line} from 'react-chartjs-2'


export default function(weight){


console.log("IN WEIGHT", weight)
var weightArr = weight.weight

const weightData = {
  labels: weightArr.map(instance=>instance.date.slice(0,10)),
  datasets:[{
    label: "baby weight",
    backgroundColor: 'rgba(75,192,192,1)',
    data: weightArr.map(instance =>(instance.weight))
  }]
}

const options ={

    maintainAspectRatio: false,
    xAxes: [{
      stacked: true,
              ticks: {
                  beginAtZero:true
              }
          }],
    yAxes: [{ticks: {
        beginAtZero:true
    }
    }]
  }



return (
  <div className="baby">
    <div>
      <h3>I'm In weight component</h3>
    </div>
    <div className="weight"></div>
    {
    weightArr.map((weight,index) => (
      <div key={index}>
        <span>{ weight.weight}</span>
      </div>
    ))

  }
  <div className="Chart">
    <Line data={weightData} width={200} height={200} options={options}/>
  </div>
  </div>
);
}

这是我的动作创建者:

import {RECEIVE_BABY} from '../constants'
import axios from 'axios'



export const receiveBaby = (baby,weight,height,sleep,diaper,feeding) =>({
  type: RECEIVE_BABY,
  baby: baby,
  weight: weight,
  feeding: feeding,
  height: height,
  sleep: sleep,
  diapers: diaper

})



export const getBabyById = babyId => {
  console.log("GET BABY BY ID")
  return dispatch => {
    Promise
      .all([
        axios.get(`/api/baby/${babyId}`),
        axios.get(`/api/baby/${babyId}/weight`),
        axios.get(`/api/baby/${babyId}/height`),
        axios.get(`/api/baby/${babyId}/sleep`),
        axios.get(`/api/baby/${babyId}/diaper`),
        axios.get(`/api/baby/${babyId}/feed`)
      ])
      .then(results => results.map(r => r.data))
      .then(results => {
        console.log("THIS IS RESULTS in Action assadkjasdfkjl;", results)
        dispatch(receiveBaby(...results));
      })
      .catch(function(err){
        console.log(err)
      })
  };
};

Here is chrome dev tools. You can see "In Weight" {weight: "undefined"} is creating the issue

您可以看到我通过“THIS IS RESULTS in Action assadkjasdfkjl; array”收到错误后的状态,但 BabyProfileContainer 和组件在收到后没有重新渲染。

【问题讨论】:

  • 当使用combineReducers 时,您实际上在状态中创建了一个新分支,因此您的映射应该相应地更改。您现在将映射state.baby.baby,而不是映射state.baby
  • 谢谢!这实际上解决了这个问题。我没有在道具上使用 baby.baby。
  • 很高兴我能帮上忙 :)

标签: javascript reactjs react-redux reducers


【解决方案1】:

在你的减速器中试试这个。类似地为其他动作类型迭代相同的代码。

   case RECEIVE_BABY:
     return {...state, baby: action.baby};
   default:
     return state;

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2017-05-15
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-01-24
    • 1970-01-01
    • 2019-08-06
    相关资源
    最近更新 更多