gdfgdfg
gdfgdfg

Reputation: 3566

Use callback in child component in React

I have parent component which renders list of child components:

renderMessages = (messages) => {
    let result = [];
    let key = 1;
    for(let i = 0; i < messages.length; i++){
        result.push(
            <Message key={key} 
                 onDeleteMessage={this.onDeleteMessage} 
                 message={messages[i]} 
             />
        );
        key++;
    }
    return result;
}

Message component (part of the render method):

<Modal
    visible={this.state.isVisible}
    onOk={this.onOkDeleteMessage}
    onCancel={this.onCancelDeleteMessage}
    destroyOnClose={true}
>
    <p>Delete Message</p>
</Modal>

In 'Message' child component, there is 'Delete' button, which on click open the modal. When 'Ok' button is pressed onOkDeleteMessage is executed and calls parent 'onDeleteMessage'.

Child component Message - onOkDeleteMessage:

onOkDeleteMessage = () => {
    this.props.onDeleteMessage(this.props.message.id);
}

This is parent component - onDeleteMessage:

    onDeleteMessage = (id) => {
    axios.delete('url here', {
        data:{id: id}})
        .then(res => {
            if(typeof res.data === 'object'){
                const id = Number(res.data.id);
                // set new state

            }
        });
};

And everything works. The problem is how to close the modal, but ONLY, if the delete request to the server is with success.

I think, one way is with callbacks -

onDeleteMessage = (id)= (id, callback) => {
  //after success request
  callback();
}

and in the child component, where onDeleteMessage is called:

onOkDeleteMessage = () => {
    this.props.onDeleteMessage(this.props.message.id, () => {
      // Change modal state
    });
}

, but I am getting this error:

Uncaught (in promise) TypeError: t is not a function

I can't add another prop from parent like this:

 <Message key={key} 
        isModalVisible
 /> 

and use state in the parent component and a prop for the child, because all modals will be open, but there are a lot of Message components.

How and which is good solution to pass that event is completed, from parent to child ?

Is there a way to use callbacks?

Upvotes: 1

Views: 1712

Answers (1)

Nisfan
Nisfan

Reputation: 746

Just add callback to onDeleteMessage.

Child component:

onOkDeleteMessage = () => {
    this.props.onDeleteMessage(this.props.message.id, () => {

        // Change modal state
    });
}

Parent component

onDeleteMessage = (id, cb) => {
    axios.delete('url here', {
        params:{id: id}})
        .then(res => {
            cb(); //this call to hide the model
        });
};

In a delete request you should use params instead of data. "data" is the data to be sent as the request bodyOnly applicable for request methods 'PUT', 'POST', and 'PATCH'

ref: https://github.com/axios/axios/issues/736

Upvotes: 3

Related Questions