TypeError: submit is not a function. In the Response Stateless component

I just get into React-Redux. I successfully connected several components to the repository using mapDispatchToPropsand mapStateToProps, therefore, my setup seems to be correct. Now I have a stateless component with a button that should send the action:

import React from 'react';
import RaisedButton from 'material-ui/RaisedButton';
import { connect } from 'react-redux';
import { bindActionCreators } from 'redux';
import { toggleSnackbar } from '../../store/actions';

const handleClick = props => {
    console.log(props.toggleSnackbar)
    props.toggleSnackbar("test")
}

const ButtonComponent = props =>
    (
      <div>
          <RaisedButton
            onClick={() => handleClick(props)}
          />
        </div>
      </div>
    );

const mapDispatchToProps = dispatch => bindActionCreators({
    toggleSnackbar,
}, dispatch);

export default connect(mapDispatchToProps)(muiThemeable()(ButtonComponent))

Now I get the error message:

Uncaught TypeError: dispatch is not a function
    at Object.toggleSnackbar (bindActionCreators.js:3)
    at handleClick (BottomCTA.jsx:28)
    at Object.onClick (BottomCTA.jsx:61)
    at EnhancedButton._this.handleClick (EnhancedButton.js:144)
    at Object../node_modules/react-dom/lib/ReactErrorUtils.js.ReactErrorUtils.invokeGuardedCallback (ReactErrorUtils.js:69)
    at executeDispatch (EventPluginUtils.js:85)
    at Object.executeDispatchesInOrder (EventPluginUtils.js:108)
    at executeDispatchesAndRelease (EventPluginHub.js:43)
    at executeDispatchesAndReleaseTopLevel (EventPluginHub.js:54)
    at Array.forEach (<anonymous>)
    at forEachAccumulated (forEachAccumulated.js:24)
    at Object.processEventQueue (EventPluginHub.js:254)
    at runEventQueueInBatch (ReactEventEmitterMixin.js:17)
    at Object.handleTopLevel [as _handleTopLevel] (ReactEventEmitterMixin.js:27)
    at handleTopLevelImpl (ReactEventListener.js:72)
    at ReactDefaultBatchingStrategyTransaction.perform (Transaction.js:143)
    at Object.batchedUpdates (ReactDefaultBatchingStrategy.js:62)
    at Object.batchedUpdates (ReactUpdates.js:97)
    at dispatchEvent (ReactEventListener.js:147)

Console Logs:

ƒ () {
    return dispatch(actionCreator.apply(undefined, arguments));
  }

toggleSnackbar action:

export function toggleSnackbar(message) {
  return {
    type: 'TOGGLE_SNACKBAR',
    payload: message,
  };
}

I can’t understand what’s wrong here?

Edit:

Here is another component in the same project that works fine with the same aciton:

import React from 'react';
import { connect } from 'react-redux';
import PropTypes from 'prop-types';
import { bindActionCreators } from 'redux';
import RaisedButton from 'material-ui/RaisedButton';
import './BuyingFormContainer.css';
import { formatDollarToFloat } from '../../shared/formater';
import { BuyingForm } from '../';
import { buyTicket, toggleSnackbar } from '../../store/actions';
import { contentEn } from '../../assets';

const customButton = {
  buttonStyle: { borderRadius: '100px', height: '40px', lineHeight: '35px' },
  overlayStyle: { borderRadius: '100px' },
  style: { borderRadius: '100px', minWidth: '200px', color: '#fffff' },
};

const handleClick = (props) => {
    console.log(props.toggleSnackbar)
  props.buyTicket(formatDollarToFloat(props.buyingForm.values.buyingFormInput));
  //TODO: Trigger this after BUY_TICKET_SUCCESS
  props.toggleSnackbar("Prediction Recieved " + props.buyingForm.values.buyingFormInput)
}

const buyingFormContainer = props => (
  <div className="buyingForm__container" id={'buyingForm'}>
    <BuyingForm />
    <RaisedButton
      label={contentEn.topComponent.buttonLabel}
      style={customButton.style}
      buttonStyle={customButton.buttonStyle}
      overlayStyle={customButton.overlayStyle}
      className="buyingForm_raisedButton"
      secondary
      onClick={() => handleClick(props)}
    />
  </div>
);

buyingFormContainer.propTypes = {
  buyTicket: PropTypes.func.isRequired,
};

const mapStateToProps = state => ({
  buyingForm: state.form.buyingForm,
});

const mapDispatchToProps = dispatch => bindActionCreators({
  buyTicket,
  toggleSnackbar,
}, dispatch);

export default connect(mapStateToProps, mapDispatchToProps)(buyingFormContainer);
+4
source share
2 answers

connectwith arity 1 uses a single argument like mapStateToProps, not mapDispatchToProps:

function mapStateToProps(state) {
  return { todos: state.todos }
}

export default connect(mapStateToProps)(TodoApp)

null :

export default connect(null, mapDispatchToProps)(...)
+3

- toggleSnackbar

export function toggleSnackbar(message) {
    return (dispatch) => {
        dispatch({
          type: 'TOGGLE_SNACKBAR',
          payload: message
        });
    }
}

bindActionCreators, , :

const mapDispatchToProps = { toggleSnackbar };

muiThemeable() connect

export default muiThemeable()(connect(null, mapDispatchToProps)(ButtonComponent))
0

Source: https://habr.com/ru/post/1687025/


All Articles