question-mark
Stuck on an issue?

Lightrun Answers was designed to reduce the constant googling that comes with debugging 3rd party libraries. It collects links to all the places you might be looking at while hunting down a tough bug.

And, if you’re still stuck at the end, we’re happy to hop on a call to see how we can help out.

Discuss - Asynchronous validation

See original GitHub issue

There have been many attempts to implement async validation in the past, and it seems like it merits a discussion on what the best approach is to implement this. Making this issue as a wrapper issue for async validation in general.

Possible solutions that have been proposed / tried so far:

It would be good to discuss the benefits and drawbacks of these approaches (such as: ease of use, backwards compatibility, etc.), and see what would be the best option to do going forward. I’ve tagged the people who’ve tried to implement async validation before on this issue, but would appreciate any feedback or thoughts!

Issue Analytics

  • State:closed
  • Created 4 years ago
  • Reactions:6
  • Comments:19 (13 by maintainers)

github_iconTop GitHub Comments

4reactions
epicfaacecommented, Oct 22, 2019

@thijssteel @beskhue continuing the conversation from #1444 on this thread, as it seems more appropriate

Here’s the concern I have about using an extraErrors prop as done in #1444: for the common scenario in which a server-side request is sent to do validation, it takes a lot of code to get this right. A good solution must:

  • In onSubmit, call the server-side request, get the errors, then set the extraErrors prop if there are errors; otherwise, submit.
  • Make sure that someone cannot call onSubmit once again before the previous server-side request, to avoid a race case.

Here’s how that might look in practice:

class App extends React.Component {
  constructor(props) {
    super(props);
    this.state = {
      validating: false,
      extraErrors: null
    }
  }
  async onSubmit(e) {
    if (this.state.validating) {
      return;
    }

    this.setState({validating: true});
    const response = await fetch("/validate");
    if (response.body.success) {
      // Now we've submitted the form.
      console.log("submitted form");
    }
    else {
      this.setState({
        validating: false,
        extraErrors: response.body.extraErrors,
      });
    }
  }
  render() {
    return <Form
      onSubmit={this.onSubmit}
      extraErrors={this.props.extraErrors}
    />
  }
}

Note that because of these constraints, we have to use a class-based component. Additionally, onSubmit is not just called on submission; it’s essentially used to perform async validation as well.

Whereas, if we just allow for an async validate function, it seems more intuitive – onSubmit is called only on form submission, and validate is used for form validation:

const onSubmit = () => {
  console.log("submitted form");
}
const validate = async (formData, errors) => {
  const response = await fetch("/validate");
  if (!response.body.success) {
    errors = {...errors, response.extraErrors};
  }
  return errors;
}
const App = () => <Form
  onSubmit={onSubmit}
  validate={validate}
/>;

@a-b-r-o-w-n

@epicfaace one advantage is that it allows the caller to fully control the validation cycle. Giving control to the library to invoke a validate() function limits my ability to control when that gets invoked.

For instance, if I have an expensive operation to validate (i.e a network request), I may only want to do that under certain conditions.

I see your point here – I think it makes sense to have an errors and onValidate(errors) prop. It would allow for full flexibility, although perhaps for the common use case of async validation it might be simpler for the user to implement it using the async validate function.

3reactions
tomcurcommented, Sep 29, 2019

@epicfaace In general I like the idea of async validation. Note there is also a race condition between validation and submission: e.g. a sign up form could validate a username for availability, but between successful validation and submission the username can be taken by someone else. Submission errors and validation errors are separate kinds in that respect.

When interacting with APIs, submission errors are almost always available. I don’t know of many APIs providing validation endpoints.

As a separate thought: perhaps for ease of use, validation can be made to be more granular: e.g. declaring validation callbacks for individual fields/objects.

Read more comments on GitHub >

github_iconTop Results From Across the Web

Creating Angular Synchronous and Asynchronous Validators ...
The most common use case for async Validators is doing a server validation via an HTTP Callback. I'll look at creating the sync...
Read more >
Using Custom Async Validators in Angular Reactive Forms
First, let's talk about Validators. What is a validator, and how we can use them to improve our forms. Ocasionally, we want to...
Read more >
Async Validation In Angular - C# Corner
In this article, I will explain how to implement Async Validation In Angular. Angular does not provide built-in type async Validation ...
Read more >
Angular Async Validator Example - TekTutorialsHub
In this guide let us learn how to create a custom async validator in Angular. The creating an async validator is very similar...
Read more >
yiminghe/async-validator: validate form asynchronous - GitHub
callback : A callback function to invoke when validation completes (optional). The method will return a Promise object like: then() ,validation passed; catch({ ......
Read more >

github_iconTop Related Medium Post

No results found

github_iconTop Related StackOverflow Question

No results found

github_iconTroubleshoot Live Code

Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start Free

github_iconTop Related Reddit Thread

No results found

github_iconTop Related Hackernoon Post

No results found

github_iconTop Related Tweet

No results found

github_iconTop Related Dev.to Post

No results found

github_iconTop Related Hashnode Post

No results found