ReactJS ajax响应错误呈现在组件中

时间:2022-08-06 20:14:36

I want to render my json response errors after ajax call in my 'FormError' component.

我想在我的'FormError'组件中调用ajax之后渲染我的json响应错误。

My error component looks like this:

我的错误组件如下所示:

var FormError = React.createClass({
    render: function () {
        return (
            <span className="form-error"></span>
        );
    }
});

My form:

var EmailForm = React.createClass({
    getInitialState: function(){
      return {
          password:'',
          email: ''
      };
    },

    componentDidMount: function() {
        this.serverRequest = $.get('/accounts/email-form/', function (result) {
          var userInfo = result;
          this.setState({
            email: userInfo.email
          });
        }.bind(this));
    },

    submit: function (e){
      var self;

      e.preventDefault()
      self = this;

      console.log(this.state);

      var data = {
        password: this.state.password,
        email: this.state.email,
        CSRF: csrftoken
      };

      // Submit form via jQuery/AJAX
      function csrfSafeMethod(method) {
            // these HTTP methods do not require CSRF protection
            return (/^(GET|HEAD|OPTIONS|TRACE)$/.test(method));
      }
      $.ajaxSetup({
            beforeSend: function(xhr, settings) {
                if (!csrfSafeMethod(settings.type) && !this.crossDomain) {
                    xhr.setRequestHeader("X-CSRFToken", csrftoken);
                }
            }
      });
      $.ajax({
        type: 'POST',
        url: '/accounts/email-form/',
        data: data
      })
      .done(function(data) {
        toastr.success('Profile updated');
      })
      .fail(function(jqXhr) {
        toastr.error('There is some errors in your request');
      });

    },

    passwordChange: function(e){
      this.setState({password: e.target.value});
    },

    emailChange: function(e){
     this.setState({email: e.target.value});
    },

    render: function() {
        return (
            <form onSubmit={this.submit}>
                <div className="form-half">
                    <label htmlFor="password" className="input-label">Current Password</label>
                    <BasicInputPassword valChange={this.passwordChange} val={this.state.password}/>
                    <FormError/>
                </div>
                <div className="form-half">
                    <label htmlFor="lastname" className="input-label">New email</label>
                    <BasicInput valChange={this.emailChange} val={this.state.email}/>
                    <FormError/>
                </div>
                 <button type="submit" className="button secondary" >Submit</button>
            </form>
        );
    }
});

This code works, ajax call give me response json with errors

这段代码有效,ajax调用给我带有错误的响应json

{"email":["Email already exists."],"password":["This field may not be blank."]}

but I haven't idea how can I append this errors to my code and my react component.

但是我不知道如何将这些错误附加到我的代码和我的反应组件中。

2 个解决方案

#1


1  

Have a separate state variable for errors and every time the json response contains errors, update the variable. Then, for instance, you could show the details to user using this condition (having errors as an empty array if there are no errors):

有一个单独的错误状态变量,每次json响应包含错误时,都要更新变量。然后,例如,您可以使用此条件向用户显示详细信息(如果没有错误,则将错误作为空数组):

{this.state.errors.length != 0 && ... // traverse them and show details

#2


0  

Why not just set an error state?!

为什么不设置错误状态?!

Could something like this:

可能是这样的:

var EmailForm = React.createClass({
constructor(props) {
  this.onError = this.onError.bind(this);
}

getInitialState: function(){
  return {
      password:'',
      email: ''
  };
},

componentDidMount: function() {
    this.serverRequest = $.get('/accounts/email-form/', function (result) {
      var userInfo = result;
      this.setState({
        email: userInfo.email
      });
    }.bind(this));
},

submit: function (e){
  var self;

  e.preventDefault()
  self = this;

  console.log(this.state);

  var data = {
    password: this.state.password,
    email: this.state.email,
    CSRF: csrftoken
  };

  // Submit form via jQuery/AJAX
  function csrfSafeMethod(method) {
        // these HTTP methods do not require CSRF protection
        return (/^(GET|HEAD|OPTIONS|TRACE)$/.test(method));
  }
  $.ajaxSetup({
        beforeSend: function(xhr, settings) {
            if (!csrfSafeMethod(settings.type) && !this.crossDomain) {
                xhr.setRequestHeader("X-CSRFToken", csrftoken);
            }
        }
  });
  $.ajax({
    type: 'POST',
    url: '/accounts/email-form/',
    data: data
  })
  .done(function(data) {
    toastr.success('Profile updated');
  })
  .fail(function(jqXhr) {
    self.onError(jqXhr.response);
    toastr.error('There is some errors in your request');
  });

},

onError: function(response) {
  this.setState({
   passwordError: response.password,
   emailError: response.email
  })
}

passwordChange: function(e){
  this.setState({password: e.target.value});
},

emailChange: function(e){
 this.setState({email: e.target.value});
},

render: function() {
   const {emailError, passwordError} = this.state;

    return (
        <form onSubmit={this.submit}>
            <div className="form-half">
                <label htmlFor="password" className="input-label">Current Password</label>
                <BasicInputPassword valChange={this.passwordChange} val={this.state.password}/>
                {emailError && <FormError error={emailError}/>}
            </div>
            <div className="form-half">
                <label htmlFor="lastname" className="input-label">New email</label>
                <BasicInput valChange={this.emailChange} val={this.state.email}/>
                {passwordError && <FormError error={passwordError}/>}
            </div>
             <button type="submit" className="button secondary" >Submit</button>
        </form>
    );
}
});

Its a bit simplified..

它有点简化..

#1


1  

Have a separate state variable for errors and every time the json response contains errors, update the variable. Then, for instance, you could show the details to user using this condition (having errors as an empty array if there are no errors):

有一个单独的错误状态变量,每次json响应包含错误时,都要更新变量。然后,例如,您可以使用此条件向用户显示详细信息(如果没有错误,则将错误作为空数组):

{this.state.errors.length != 0 && ... // traverse them and show details

#2


0  

Why not just set an error state?!

为什么不设置错误状态?!

Could something like this:

可能是这样的:

var EmailForm = React.createClass({
constructor(props) {
  this.onError = this.onError.bind(this);
}

getInitialState: function(){
  return {
      password:'',
      email: ''
  };
},

componentDidMount: function() {
    this.serverRequest = $.get('/accounts/email-form/', function (result) {
      var userInfo = result;
      this.setState({
        email: userInfo.email
      });
    }.bind(this));
},

submit: function (e){
  var self;

  e.preventDefault()
  self = this;

  console.log(this.state);

  var data = {
    password: this.state.password,
    email: this.state.email,
    CSRF: csrftoken
  };

  // Submit form via jQuery/AJAX
  function csrfSafeMethod(method) {
        // these HTTP methods do not require CSRF protection
        return (/^(GET|HEAD|OPTIONS|TRACE)$/.test(method));
  }
  $.ajaxSetup({
        beforeSend: function(xhr, settings) {
            if (!csrfSafeMethod(settings.type) && !this.crossDomain) {
                xhr.setRequestHeader("X-CSRFToken", csrftoken);
            }
        }
  });
  $.ajax({
    type: 'POST',
    url: '/accounts/email-form/',
    data: data
  })
  .done(function(data) {
    toastr.success('Profile updated');
  })
  .fail(function(jqXhr) {
    self.onError(jqXhr.response);
    toastr.error('There is some errors in your request');
  });

},

onError: function(response) {
  this.setState({
   passwordError: response.password,
   emailError: response.email
  })
}

passwordChange: function(e){
  this.setState({password: e.target.value});
},

emailChange: function(e){
 this.setState({email: e.target.value});
},

render: function() {
   const {emailError, passwordError} = this.state;

    return (
        <form onSubmit={this.submit}>
            <div className="form-half">
                <label htmlFor="password" className="input-label">Current Password</label>
                <BasicInputPassword valChange={this.passwordChange} val={this.state.password}/>
                {emailError && <FormError error={emailError}/>}
            </div>
            <div className="form-half">
                <label htmlFor="lastname" className="input-label">New email</label>
                <BasicInput valChange={this.emailChange} val={this.state.email}/>
                {passwordError && <FormError error={passwordError}/>}
            </div>
             <button type="submit" className="button secondary" >Submit</button>
        </form>
    );
}
});

Its a bit simplified..

它有点简化..