Categories
Development iOS

Sending data to store with action, and making axios post request on same button click. Axios posts before the store data comes

Container: Login
Child components: => ContentBox => Form

This is Login Container:

const mapStateToProps = state => {
    return { userCredentials: state.userLogin };
};

const Login = ( props ) => {

    const postLogin = ( e ) => {
        axios( {
            method: "POST",
            url: "http://localhost:8080/api/login-user",
            data: {
                email: props.userCredentials.email,
                password: props.userCredentials.password
            }
        } ).then( ( response ) => console.log( response ) ).catch( ( e ) => console.log( e ) );
    };


    return (
        <div id={"login"}>
            <ContentBox submitLogin={postLogin}/>
        </div>
    );
};

export default connect( mapStateToProps )( Login );

And the Form Child Component:

const mapStateToProps = state => {
    return { stateInput: state.loginInput };
};

const Form = ( props ) => {
    const [ input, setInput ] = useState( { email: "", password: "" } );

    const handleEmail = ( event ) => {
        setInput( { ...input, email: event.target.value } );
    };

    const handlePassword = event => {
        setInput( { ...input, password: event.target.value } );
    };

    const submitDispatch = () => {
        store.dispatch( {
            type: "LOGIN_INPUT",
            payload: { email: input.email, password: input.password }
        } );
    };

    const submitForm = ( props ) => {
        props.submitLogin();
    };

    return (
        <div className={"form"} id={"loginForm"}>
            <button onClick={() => store.dispatch( {
                type: "LOGIN_INPUT",
                payload: { email: input.email, password: input.password }
            } )}>DISPATCH
            </button>
            <form method={"POST"}>
                <input value={input.email} onChange={handleEmail} name={"email"} type="text"
                       placeholder={props.placeholder[0]}/>
                <input value={input.password} onChange={handlePassword} name={"password"} type="text"
                       placeholder={props.placeholder[1]}/>

                <button className={"submit-button"} onClick={( e ) => {
                    e.preventDefault();
                    submitDispatch();
                    submitForm( props );

                }}>LOGIN
                </button>

            </form>

        </div>
    );
};


export default connect( mapStateToProps )( Form );

And then the reducer:

const initialState = {
    userLogin: {
        email: "",
        password: ""
    }
};

function rootReducer( state = initialState, action ) {
    if ( action.type === LOGIN_INPUT ) {
        return {
            ...state,
            userLogin: {
                email: action.payload.email,
                password: action.payload.password
            }
        };
    }
    return state;
}

export default rootReducer;

Now the issue:

In the Form Component, I have a button that triggers an action with redux, which sends what the user typed in the input fields (Email and password), this works correctly with the store, and I do receive it in the Login container in the form of props.userCredentials.

However: In the same button, I also want to trigger the axios call to post to my node backend, to find a user. But when I do, the axios call always receives the initial state of “” in email and password, but when I log the props.userCredentials in the Form container, I do receive the new state from redux.

I tried setting a setTimeout in the Form container and log the redux store, however then every other log I receive “”, and the other log I receive the actual correct state.

How to best achieve this set up, with the button (on the form), to have both the axios call and the send to redux store?

The reason I have it like this is because I want the containers to make the axios calls, and the containers to not contain any JSX (easier to read), so I had to pass the axios call function down as props to the children.

Thank you so much for your help!

Leave a Reply

Your email address will not be published. Required fields are marked *