React JS-显示状态值取决于redux props值

时间:2019-09-12 08:50:55

标签: javascript reactjs redux react-props

我有一个组件,在该组件中,我想显示状态取决于props值的值。 我总是会遇到错误,无法在线找到一个很好的例子。

这是我的组件(波纹管),我想在this.state.msg等于this.props.passRecoveryEditSuccess.password_changed时显示1

我编写了massage函数,该函数应根据减速器返回的内容来设置msg的状态。

问题是我不断得到即将来临的结果: enter image description here

我该如何解决这个问题?

`

import React, { Component } from 'react';
import {Form, Alert, FormGroup, Col, Button, FormControl, Grid} from 'react-bootstrap';
import {connect} from 'react-redux';
import {Link} from 'react-router-dom';
import Header from '../header/Header';
import { PassRecoveryEdit } from '../../actions/ajax';

class PasswordRecoveryEdit extends Component {
    constructor(props){
        super(props);
        this.state ={
            password: '',
            confirmPassword: '',
            msg: ''
        } 
    }

    componentDidUpdate(){
        if(this.props.passRecoveryEditSuccess){
            this.massage()
        }
    }
    onChange = (e) => {
       this.setState({
            [e.target.name]: e.target.value
        })  
    }


    formValidation = () => {
        let isError = false;
        const errors = {};

        if(this.state.password.length < 6){
            isError =  true;
            errors.passwordLengthError = "על הסיסמה להיות ארוכה מ 6 תווים"
          }else{
            isError =  false;
            errors.passwordLengthError = ""
          }

          if( this.state.confirmPassword !==  this.state.password){
            isError =  true;
            errors.passwordMatchError = "הסיסמאות לא תואמות"

          }else{
            isError =  false;
            errors.passwordMatchError = ""
          }

        this.setState({
            ...this.state,
            ...errors
        });
        return isError
    }

    onSubmit = (e) => {
        e.preventDefault();
        //console.log('onSubmit');
        //console.log('this.state', this.state);

        let obj = {
            password: this.state.password,
            token: this.props.match.params.token
        }
    let err = this.formValidation();
        if(!err){
            this.props.PassRecoveryEdit(obj);
        // console.log('success');
        }

    }

    massage = () => {
        if(this.props.passRecoveryEditSuccess.password_changed == 1){
            this.setState({msg: 'הסיסמה עודכנה בהצלחה '});
        }else{
            this.setState({msg: 'הסיסמה לא עודכנה בהצלחה'});
        }
    }


    render() {
        return (
            <div>
                <Header headline="הזינו סיסמה חדשה"/>
                <Grid>
                    <Form horizontal onSubmit={this.onSubmit.bind(this)}>  
                        <FormGroup>
                            <FormControl 
                                ref="password"
                                name="password"
                                id="password"
                                type="password"
                                placeholder="הקלידו את הסיסמה"
                                aria-label="הקלידו את הסיסמה"
                                onChange={this.onChange.bind(this)}
                            />    
                        </FormGroup>
                        {this.state.passwordLengthError  &&
                            <Alert variant="danger" className="text-right">
                                {this.state.passwordLengthError}
                            </Alert>    
                        }

                        <FormGroup>
                            <FormControl 
                                ref="confirmPassword"
                                name="confirmPassword"
                                id="confirmPassword"
                                type="password"
                                placeholder="הקלידו הסיסמה שנית"
                                aria-label="הקלידו הסיסמה שנית"
                                onChange={this.onChange.bind(this)}
                            />    
                        </FormGroup>
                        {this.state.passwordMatchError  &&
                            <Alert variant="danger" className="text-right">
                                {this.state.passwordMatchError}
                            </Alert>    
                        }
                        <FormGroup>
                        <Col xs={12}>
                          <Button className="full-width-btn" type="submit">שינוי סיסמה</Button>
                        </Col>
                      </FormGroup>
                    </Form>

                    {this.state.msg && 

                        <Alert variant="danger" className="text-right">

                        {this.state.msg}

                    </Alert>   
                    }
                </Grid>
            </div>
        )
    }
}

const mapStateToProps = state => {
    return{
            passRecoveryEditSuccess: state.userReducer.passRecoveryEdit
    }
}


export default connect(mapStateToProps, {PassRecoveryEdit})(PasswordRecoveryEdit)

`

1 个答案:

答案 0 :(得分:2)

您正在创建一个无限循环。只要您的状态或道具在组件中发生更改,就会调用componentDidUpdate()。因此,在第一个渲染之后,您将从redux获取更新的道具,因此componentDidUpdate()触发,条件通过,然后调用this.massage()

然后this.massage()更新组件的状态,重新触发componentDidUpdate(),这在调用this.massage()之前正在检查完全相同的条件,从而创建了循环。

您可以做的是在prevProps中使用componentDidUpdate()参数,并使用它创建一个更受保护的条件。

componentDidUpdate(prevProps){
    if(this.props.passRecoveryEditSuccess !== prevProps.passRecoveryEditSuccess){
        this.massage()
    }
}

用这个意思是,当属于先前渲染的道具不等于新渲染时,您只会调用this.massage()