Nehemah
Nehemah

Reputation: 13

ReactJS : infinite loop rendering component

I have an issue on ReactJS about an infinite loop of an Axios request link to a componentDidMount function.

Here the thing :

To check the token, I made a POST request via a componentDidMount.

Finally, I get the right render BUT my request is call again and again, creating an infinite loop on my server. It seems that my child component is re-construct again and again.

Here's my code :

Child component :

import React from 'react';
import {Container} from 'reactstrap';

export default class ResetPassword extends React.Component {

    constructor(props) {
        super(props);
        console.log('CONSTRUCT')
    }

    componentDidMount() {
if (this.props.appState.loading ≡ false) {
            console.log('componentDidMount')
            let url = window.location.pathname;
            let verifToken = url.substr(15);
            this.props.checkToken(verifToken); //Make axios call on App.js
        }
   }

    render() {
        const {expiredToken} = this.props.appState;
        console.log(expiredToken)
        return (
            <div className="ResetPassword">
                <Container>
                    {expiredToken === true ?
                        (<div>VOTRE TOKEN A EXPIRE</div>
                        ) : (<div>CHANGER MON MOT DE PASSE</div>)}
                </Container>
            </div>
        )
    }
}    

Parent Component :

import axios from 'axios';
import ResetPassword from "./components/SignUp/ResetPwd";

class App extends React.Component {    
    constructor(props) {
        super(props);
        this.state = {
             loading: false,
             expiredToken : null
        };
        this.checkToken = this.checkToken.bind(this);
    }

    checkToken(token) {
        console.log('checkToken');
        this.setState({loading: true}, () => {
            let url = `${this.state.config.apiURL}/checkToken`;
            let method = 'post';
            axios.request({
                url: url,
                method: method,
                data: {
                    token: token
                }
            }).then(results => {
                if (results.data === null) {
                    this.setState({
                        loading: false,
                        expiredToken: true
                    })
                } else {
                    console.log(results.data);
                    this.setState({
                        loading: false,
                        expiredToken: false
                    });
                }
            })
        })
    }

    render() {
        const ResetPwd = (props) => {
            return (
                <div>
                    <ResetPassword appState={this.state} {...props} checkToken={this.checkToken}/>    
                </div>
            )
        };
    }
}         

And in my console DevTool, I have my 5 console.log() which turn into an infinite loop :

Upvotes: 0

Views: 7249

Answers (2)

Helmer Barcos
Helmer Barcos

Reputation: 2076

i think after you load the childComponent for fist time and the function checkToken is called, the state loading is setted to false. you are also forcing a rerender from the parentcomponent with setSatate and with it you are forcing also the mounting from the Chilcomponent and the componentDidMount method from the child. after the first render if you try to print the loading state im sure it would be always false, after first true.

try to create local states for each child or think again a new implementation of the function.

Upvotes: -1

RIYAJ KHAN
RIYAJ KHAN

Reputation: 15292

Remove checkToken from ResetPassword component.

Instead of calling checkToken from ResetPassword,called it within Parent component and pass the data using state to ResetPassword component..

  <ResetPassword appState={...this.state} {...props}/>

Upvotes: 3

Related Questions