Reactjs 操作未将数据传递给减速器

Reactjs 操作未将数据传递给减速器,reactjs,redux,react-redux,Reactjs,Redux,React Redux,我有以下设置: Dashboard.jsx: import React, { Component } from "react"; import { addFlashMessage } from "../actions/flashMessages"; import RoomsList from "./RoomsList"; import PropTypes from "prop-types"; import FlashMessagesList from "../components/flash/F

我有以下设置:

Dashboard.jsx:

import React, { Component } from "react";
import { addFlashMessage } from "../actions/flashMessages";
import RoomsList from "./RoomsList";
import PropTypes from "prop-types";
import FlashMessagesList from "../components/flash/FlashMessagesList";
import { connect } from "react-redux";

class Dashboard extends Component {
  render() {
    return (
      <div className="componentContent">
        <FlashMessagesList />
        <RoomsList addFlashMessage={addFlashMessage} />
      </div>
    );
  }
}
Dashboard.propTypes = {
  addFlashMessage: PropTypes.func.isRequired
};

export default connect(null, { addFlashMessage })(Dashboard);
import React, { Component } from "react";
import PropTypes from "prop-types";

class RoomsList extends Component {
  constructor(props) {
    super(props);
    this.onClick = this.onClick.bind(this);
  }
  onClick() {
    this.props.addFlashMessage({
      type: "success",
      text: "You signed up successfully. Welcome."
    });
  }
  render() {
    return (
      <div className="componentContent" onClick={this.onClick} />
    );
  }
}

RoomsList.propTypes = { addFlashMessage: PropTypes.func.isRequired };

export default RoomsList;
export function addFlashMessage(message) {
  console.log("action called");
  return {
    type: ADD_FLASH_MESSAGE,
    message
  };
}
import React from "react";
import ReactDOM from "react-dom";
import App from "./components/App";
import { BrowserRouter as Router, Route } from "react-router-dom";

// Redux
import { Provider } from "react-redux";
import thunk from "redux-thunk";
import { createStore, applyMiddleware, compose } from "redux";
import rootReducer from "./rootReducer";

const store = createStore(
  rootReducer,
  compose(
    applyMiddleware(thunk),
    window.devToolsExtension ? window.devToolsExtension() : f => f
  )
);

ReactDOM.render(
  <Provider store={store}>
    <Router>
      <div className="navSwitch">
        <Route path="/" component={App} />
      </div>
    </Router>
  </Provider>,
  document.getElementById("root")
);
Reducers.js

import { ADD_FLASH_MESSAGE } from "../actions/types";
import shortid from "shortid";

export default (state = [], action = {}) => {
  console.log(action);
  switch (action.type) {
    case ADD_FLASH_MESSAGE:
      return [
        ...state,
        {
          id: shortid.generate(),
          type: action.message.type,
          text: action.message.text
        }
      ];
    default:
      return state;
  }
};
index.js:

import React, { Component } from "react";
import { addFlashMessage } from "../actions/flashMessages";
import RoomsList from "./RoomsList";
import PropTypes from "prop-types";
import FlashMessagesList from "../components/flash/FlashMessagesList";
import { connect } from "react-redux";

class Dashboard extends Component {
  render() {
    return (
      <div className="componentContent">
        <FlashMessagesList />
        <RoomsList addFlashMessage={addFlashMessage} />
      </div>
    );
  }
}
Dashboard.propTypes = {
  addFlashMessage: PropTypes.func.isRequired
};

export default connect(null, { addFlashMessage })(Dashboard);
import React, { Component } from "react";
import PropTypes from "prop-types";

class RoomsList extends Component {
  constructor(props) {
    super(props);
    this.onClick = this.onClick.bind(this);
  }
  onClick() {
    this.props.addFlashMessage({
      type: "success",
      text: "You signed up successfully. Welcome."
    });
  }
  render() {
    return (
      <div className="componentContent" onClick={this.onClick} />
    );
  }
}

RoomsList.propTypes = { addFlashMessage: PropTypes.func.isRequired };

export default RoomsList;
export function addFlashMessage(message) {
  console.log("action called");
  return {
    type: ADD_FLASH_MESSAGE,
    message
  };
}
import React from "react";
import ReactDOM from "react-dom";
import App from "./components/App";
import { BrowserRouter as Router, Route } from "react-router-dom";

// Redux
import { Provider } from "react-redux";
import thunk from "redux-thunk";
import { createStore, applyMiddleware, compose } from "redux";
import rootReducer from "./rootReducer";

const store = createStore(
  rootReducer,
  compose(
    applyMiddleware(thunk),
    window.devToolsExtension ? window.devToolsExtension() : f => f
  )
);

ReactDOM.render(
  <Provider store={store}>
    <Router>
      <div className="navSwitch">
        <Route path="/" component={App} />
      </div>
    </Router>
  </Provider>,
  document.getElementById("root")
);
从“React”导入React;
从“react dom”导入react dom;
从“/components/App”导入应用程序;
从“react Router dom”导入{BrowserRouter as Router,Route};
//重演
从“react redux”导入{Provider};
从“redux thunk”导入thunk;
从“redux”导入{createStore,applyMiddleware,compose};
从“/rootReducer”导入rootReducer;
const store=createStore(
减根剂,
谱写(
applyMiddleware(thunk),
window.devToolsExtension?window.devToolsExtension():f=>f
)
);
ReactDOM.render(
,
document.getElementById(“根”)
);
actions.js
console.log显示为ok,但在
reducer.js
中,console.log未被执行,因此只返回默认状态


有人能发现问题出在哪里吗?

仪表板
组件中,您通过
道具
向组件传递
添加FlashMessage
操作,但在组件内部,您使用的是导入的功能,而不是传递的功能。它们看起来是一样的(因为它们实际上是同一函数的不同版本),但由于导入的函数未包装在
dispatch()
中,因此对它的调用不会触发Redux操作


修复是显而易见的-您需要在这里使用
这个.props.addFlashMessage

仪表板中
您通过
props
addFlashMessage
操作传递给组件,但在组件内部您使用的是导入的函数,而不是传递的。它们看起来是一样的(因为它们实际上是同一函数的不同版本),但由于导入的函数未包装在
dispatch()
中,因此对它的调用不会触发Redux操作


修复是显而易见的-您需要使用
this.props.addFlashMessage
此处:

Redux开发工具对于类似的事情是一个很好的帮助-值得使用它只是为了看看某个操作是否真的启动,如果是,至少您知道它在减速器中,如果没有,动作没有被分派Edux dev tools对于类似的事情是一个很好的帮助-值得使用它只是为了看看动作是否真正激发,如果是这样,至少你知道它在减速器中,如果操作未被分派,则会导致
失败的道具类型:道具“addFlashMessage”在
仪表板
中标记为必需,但其值为“未定义”。
当然,因为我的示例返回
{actions:addFlashMessage}
。建议使用这种方法,因为通常在组件中有多个操作。您可以返回单个操作,也可以更新
propTypes
定义,改为使用
actions:propTypes.object.isRequired
。您还需要更新组件内部的操作引用。但这并不是问题的真正原因,因为我的方法可以使用,我们可以在这里阅读:所以问题必须在其他地方。@Xeen您是对的,对不起,不知道这种速记语法。我也被辛普敦搞糊涂了。然而,我看到了问题的真正原因,我现在将更新答案如果你看我的代码,我已经在这样做:)所以这是另一回事。这导致
失败的道具类型:道具“addFlashMessage”在
仪表板
中标记为必需,但其值是“未定义的”。
当然,因为我的示例返回
{操作:addFlashMessage}
。建议使用这种方法,因为组件中通常有多个操作。您可以返回单个操作,也可以更新
propTypes
定义,使其具有
操作:propTypes.object.isRequired
。您还需要更新组件内的操作引用。但这并不是真正的原因我的方法可以用来解决这个问题,我们可以在这里阅读:所以问题必须在其他地方。@Xeen你是对的,对不起,没有意识到这种速记语法。我也被Symptom搞糊涂了。但是我看到了问题的真正原因,我现在会更新答案,如果你看我的代码,我已经在做了:)所以这是一些问题还有一个。