2
votes

I have a Vue component that contains a form with the Vuelidate form validation plugin installed and I want to make an API call with Axios to check if a username is already taken in the database. There is no functionality yet to actually display anything if a username is indeed taken, but the Vuelidate object $v should still be reactive and update its username prop according to my Axios API call.

Join.vue

<template>
<form id="join">
<input
          name="username"
          placeholder="Username"
          v-model.lazy="username"
          @blur="$v.username.$touch()"
          type="text"
          autocomplete="off"
        />
... (submit button and other irrelevant stuff) ...
</form>
</template>
<script>
import { required } from 'vuelidate/lib/validators'
import Api from '@/services/Api'
export default {
  data() {
    return {
      username: ''
    }
  },
  validations: {
    username: {
      required,
      isUnique(username) {
        if (username === '') return true

        return Api()
          .get('/validate', {
            params: { field: 'username', value: username }
          })
          .then(res => {
            console.log(res.data)
            return res.data.status
          })
          .catch(error => {
            console.error(error)
          })
      }
    }
  }
}
</script>

The Axios call gets a proper JSON response from the API that shows up in the Chrome DevTools (status 200 OK):

/validate?field=username&value=Test (username available)

{"status":true}

/validate?field=username&value=Admin (username taken)

{"status":false}

Expected result and issue:

isUnique() should make the API call and after getting a response, return a value of either true or false depending on whether the user name is already taken or not (res.data.status). Then, the properties of $v should change accordingly for the form to be validated.

The response gets logged properly in the Javascript Console. However, $v.username is ALWAYS invalid ($v.username.$invalid: true), even when the console logs { status: true }.

Also, it seems that either the Axios .then promise doesn't resolve properly, or that the Vuelidate does not receive the resolved value, as $pending is still set to true after validating the input field and logging the response.

Before changing the value of the input field, $pending is set to false.

There are no errors in the console or when building my Vue app. How can I make Vuelidate await the response and then actually make isUnique() return the proper boolean?

1
Show the code for Api() as well, pleaseStyx

1 Answers

2
votes

I was able to resolve this by adding async to the isUnique() method.