React Redux无法让减速器拾取动作

React Redux cant get reducer to pick up actions

本文关键字:减速器 Redux React      更新时间:2023-09-26

我一直在学习redu&做出反应,正在建立一个待办事项列表。我一直在阅读和查看不同的文章,但无法弄清楚我的设置中缺少了什么。

目前,您可以通过输入添加待办事项。在按下回车键时,它会发送一个带有todo文本的addTodo操作。

我希望reducer看到操作类型并更新状态,但它从来没有看到。我错过了什么?

index.jsx

import React from 'react';
import ReactDOM from 'react-dom';
import { createStore } from 'redux';
import { Provider } from 'react-redux';
import reducer from './reducer.js';
import TodoList from './containers/container.js';
const store = createStore(reducer);
ReactDOM.render(
  <Provider store={store}>
    <TodoList />
  </Provider>,
document.getElementById('app'));

actions.js

var uuid = require('node-uuid');
export function addTodo(text) {
  console.log('action addTodo', text);
  return {
    type: 'ADD_TODO',
    payload: {
      id: uuid.v4(),
      text: text
    }
  };
}

TodoListComponent.jsx

import React from 'react';
import TodoComponent from './TodoComponent.jsx';
import { addTodo } from '../actions/actions.js'
export default class TodoList extends React.Component {
  render () {
    const { todos } = this.props;
    return (
      <div>
        <input type='text' placeholder='Add todo' onKeyDown={this.onSubmit} />
        <ul>
          {todos.map(c => (
            <li key={t.id}>
              <TodoComponent todo={t} styleName='large' />
            </li>
          ))}
        </ul>
      </div>
    )
  }
  onSubmit(e) {
    const input = e.target;
    const text = input.value;
    const isEnterKey = (e.which === 13);
    if (isEnterKey) {
      input.value = '';
      addTodo(text);
    }
  }
}

TodoComponent.jsx

import React from 'react';
import CSSModules from 'react-css-modules';
import styles from './style.css';
export default class TodoComponent extends React.Component {
  render () {
    const { todo } = this.props;
    return (
      <div styleName='large'>{todo.text}</div>
    )
  }
}
export default CSSModules(TodoComponent, styles);

container.js

import { connect } from 'react-redux';
import TodoList from '../components/TodoListComponent.jsx';
import { addTodo } from '../actions/actions.js';
const mapStateToProps = (state) => {
   return {
      todos: state
   }
};
const mapDispatchToProps = (dispatch) => {
   return {
      addTodo: text => dispatch(addTodo(text))
   }
};
export default connect(mapStateToProps, mapDispatchToProps)(TodoList);

减速器.js

import { List, Map } from 'immutable';
const init = List([]);
export default function(todos = init, action) {
  console.log('reducer action type', action.type);
  switch(action.type) {
    case 'ADD_TODO':
      console.log('ADD_TODO');
      return todos.push(Map(action.payload));
    default:
      return todos;
  }
}

TodoListComponent中,您直接从操作文件导入操作,但实际上您希望使用映射到调度的操作,并将其作为容器中的属性传递。这就解释了为什么您看到的是来自操作的日志,而不是来自reducer的日志,因为操作从未调度到存储。

所以你的TodoListComponent应该是:

import React from 'react';
import TodoComponent from './TodoComponent.jsx';
export default class TodoList extends React.Component {
  render () {
    const { todos } = this.props;
    return (
      <div>
        <input type='text' placeholder='Add todo' onKeyDown={this.onSubmit} />
        <ul>
          {todos.map(c => (
            <li key={t.id}>
              <TodoComponent todo={t} styleName='large' />
            </li>
          ))}
        </ul>
      </div>
    )
  }
  onSubmit(e) {
    const input = e.target;
    const text = input.value;
    const isEnterKey = (e.which === 13);
    if (isEnterKey) {
      input.value = '';
      this.props.addTodo(text);
    }
  }
}
import React from 'react';
import TodoComponent from './TodoComponent.jsx';
export default class TodoList extends React.Component {
  render () {
    const { todos } = this.props;
    return (
      <div>
        <input type='text' placeholder='Add todo' onKeyDown={this.onSubmit.bind(this)} />
        <ul>
          {todos.map(c => (
            <li key={t.id}>
              <TodoComponent todo={t} styleName='large' />
            </li>
          ))}
        </ul>
      </div>
    )
  }
  onSubmit(e) {
    // use the addTodo passed via connect
    const { addTodo } = this.props;
    const input = e.target;
    const text = input.value;
    const isEnterKey = (e.which === 13);
    if (isEnterKey) {
      input.value = '';
      addTodo(text);
    }
  }
}