Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Vee-Validate custom date validation

I was wondering if there is anyway you can write a custom date validation using vee-validate plugin where the end date cannot be less than the start date? I have looked high and low, and there is nowhere I can find a definite answer to this.

If there is no way to implement this, then I can make do without it, however, right now what I have implemented in my template for my start date is:

<input type="text" id="startDate" name="startDate" class="form-control" v-model="startDate" v-validate="'required|date_format:DD-MM-YYYY'" :class="{'input': true, 'is-danger': errors.has('startDate') }">
    <label class="mb-0" for="startDate">Start Date</label>
        <span v-show="errors.has('startdate')" class="text-danger"><center>{{ errors.first('startdate') }}</center></span>

My script looks like this:

    export default {
    name: 'App',
    data: () => ({
        task: '',
        startDate: '',
        startTime: '',
        endDate: '',
        endTime: '',
        description: 'test'
    }),
    methods: {
        validateBeforeSubmit() {
            this.$validator.validateAll().then((result) => {
                if (result) {
                // eslint-disable-next-line
                alert('Form Submitted!');
                return;
                }

                alert('Correct them errors!');
            });
        }
    }

};

But there is no validation that is showing up. I think I am missing something in my script but I am not sure how to implement the date into there. Any help would be greatly appreciated.

like image 796
bpp Avatar asked Jan 03 '23 06:01

bpp


1 Answers

First, it's maybe some typo error but in your template you use startDate and startdate lowercased.

Then, to answer your question, it's possible to define a custom validator with a date comparison with vee-validate.

As your chosen date format "DD-MM-YYYY" is not a valid javascript Date format, the string dates need to be rewritten into a valid format to make it work.

Vue.use(VeeValidate)

new Vue({
  el: "#app",
  data() {
    return {
      startDate: '',
      endDate: '',
    }
  },
  created() {
    let self = this
    this.$validator.extend('earlier', {
      getMessage(field, val) {
        return 'must be earlier than startDate'
      },
      validate(value, field) {
        let startParts = self.startDate.split('-')
        let endParts = value.split('-')
        let start = new Date(startParts[2], startParts[1] -1, startParts[0]) // month is 0-based
        let end = new Date(endParts[2], endParts[1] -1, endParts[0])

        return end > start
      }
    })
  },
  methods: {
    validateBeforeSubmit() {
      this.$validator.validateAll().then((result) => {
        if (result) {
          alert('Form Submitted!');
          return;
        }
        alert('Correct them errors!');
      });
    }
  }
})
.is-danger, .text-danger {
  color: red;
}
<script src="https://unpkg.com/[email protected]/dist/vee-validate.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/vue/2.5.16/vue.min.js"></script>
<div id="app">
  <div>
    <input type="text" name="startDate" v-model="startDate"v-validate="'required|date_format:DD-MM-YYYY'" :class="{'input': true, 'is-danger': errors.has('startDate') }">
    <label class="mb-0" for="startDate">Start Date</label>
    <span v-show="errors.has('startDate')" class="text-danger">{{ errors.first('startDate') }}</span>
  </div>
  <div>
    <input type="text" name="endDate" v-model="endDate" v-validate="'required|date_format:DD-MM-YYYY|earlier'" :class="{'input': true, 'is-danger': errors.has('endDate') }">
    <label class="mb-0" for="endDate">End Date</label>
    <span v-show="errors.has('endDate')" class="text-danger">{{ errors.first('endDate') }}</span>  
  </div>

  <button @click="validateBeforeSubmit">Save</button>
</div>

Note: i put the custom validator inside the created hook for the example but you can put it inside any file you want in your projet. Just import it correctly as the documentation recommends.

like image 97
Sovalina Avatar answered Jan 05 '23 14:01

Sovalina