new approach for validation

This commit is contained in:
einhornimmond 2025-02-04 12:51:06 +01:00
parent ff12773188
commit 52414789cd
7 changed files with 125 additions and 48 deletions

View File

@ -29,7 +29,7 @@
"@types/leaflet": "^1.9.12",
"@vee-validate/i18n": "^4.14.7",
"@vee-validate/rules": "^4.14.1",
"@vee-validate/yup": "^4.14.1",
"@vee-validate/yup": "^4.15.0",
"@vitejs/plugin-vue": "5.1.4",
"@vue-leaflet/vue-leaflet": "^0.10.1",
"@vue/apollo-composable": "^4.0.2",
@ -68,7 +68,7 @@
"vue-timer-hook": "^1.0.84",
"vuex": "^4.1.0",
"vuex-persistedstate": "^4.1.0",
"yup": "^1.4.0"
"yup": "^1.6.1"
},
"devDependencies": {
"@apollo/client": "^3.10.8",

View File

@ -5,26 +5,18 @@
class="form-style p-3 bg-white app-box-shadow gradido-border-radius"
@submit.prevent="submit"
>
<label>{{ $t('contribution.selectDate') }}</label>
<BFormInput
<ValidatedInput
id="contribution-date"
:model-value="date"
:model-value="formValues.date"
name="date"
:state="dataFieldMeta.valid"
:locale="$i18n.locale"
:max="getMaximalDate"
:min="minimalDate.toISOString().slice(0, 10)"
class="mb-4 bg-248"
reset-value=""
:label-no-date-selected="$t('contribution.noDateSelected')"
required
:label="$t('contribution.selectDate')"
:no-flip="true"
class="mb-4 bg-248"
type="date"
@update:model-value="handleDateChange"
>
<template #nav-prev-year><span></span></template>
<template #nav-next-year><span></span></template>
</BFormInput>
:schema-description="schemaDescription.fields.date"
@update:model-value="updateField"
/>
<div v-if="showMessage" class="p-3" data-test="contribtion-message">
{{ noOpenCreation }}
</div>
@ -39,12 +31,12 @@
<input-hour
name="hours"
:label="$t('form.hours')"
placeholder="0.25"
placeholder="0.01"
:rules="{
required: true,
min: 0.25,
// decimal: 2,
min: 0.01,
max: validMaxTime,
gddCreationTime: { min: 0.25, max: validMaxTime },
}"
:valid-max-time="validMaxTime"
/>
@ -88,12 +80,14 @@
</template>
<script setup>
import { ref, computed, watch, onMounted } from 'vue'
import { ref, computed, watch } from 'vue'
import { useI18n } from 'vue-i18n'
import InputHour from '@/components/Inputs/InputHour'
import InputAmount from '@/components/Inputs/InputAmount'
import InputTextarea from '@/components/Inputs/InputTextarea'
import { useField, useForm } from 'vee-validate'
import ValidatedInput from '@/components/Inputs/ValidatedInput.vue'
import { createContributionFormValidation } from '@/validationSchemas'
import { useForm, useField } from 'vee-validate'
const props = defineProps({
modelValue: { type: Object, required: true },
@ -109,11 +103,14 @@ const { t } = useI18n()
const form = ref({ ...props.modelValue })
const validationSchema = createContributionFormValidation(t)
const schemaDescription = validationSchema.describe()
// console.log(schemaDescription)
const {
values: formValues,
meta: formMeta,
resetForm,
defineField,
setFieldValue,
} = useForm({
initialValues: {
@ -122,15 +119,15 @@ const {
hours: props.modelValue.hours,
amount: props.modelValue.amount,
},
validationSchema
})
const [date, dateProps] = defineField('date')
const { meta: dataFieldMeta } = useField('date')
const { meta: dataFieldMeta } = useField('date', 'required')
const handleDateChange = (newDate) => {
date.value = newDate
emit('update:model-value', { ...props.modelValue, date: newDate })
const updateField = (newValue, name) => {
if(typeof name === 'string' && name.length) {
setFieldValue(name, newValue)
}
}
const showMessage = computed(() => {
@ -146,8 +143,8 @@ const showMessage = computed(() => {
const disabled = computed(() => {
return (
!formMeta.value.valid ||
(props.isThisMonth && parseInt(form.value.amount) > parseInt(props.maxGddThisMonth)) ||
(!props.isThisMonth && parseInt(form.value.amount) > parseInt(props.maxGddLastMonth))
(props.isThisMonth && parseFloat(form.value.amount) > parseFloat(props.maxGddThisMonth)) ||
(!props.isThisMonth && parseFloat(form.value.amount) > parseFloat(props.maxGddLastMonth))
)
})
@ -172,15 +169,11 @@ const noOpenCreation = computed(() => {
return ''
})
const getMaximalDate = computed(() => {
return new Date().toISOString().slice(0, 10)
})
watch(
() => formValues.hours,
() => {
updateAmount(formValues.hours)
},
}
)
function updateAmount(hours) {

View File

@ -3,16 +3,15 @@
<BFormGroup :label="label" :label-for="labelFor">
<BFormInput
:id="labelFor"
:model-value="currentValue"
v-model="currentValue"
:name="name"
:placeholder="placeholder"
type="number"
:state="meta.valid"
step="0.25"
step="0.01"
min="0"
:max="validMaxTime"
class="bg-248"
@update:model-value="currentValue = $event"
/>
<BFormInvalidFeedback v-if="errorMessage">
{{ errorMessage }}

View File

@ -0,0 +1,63 @@
<template>
<div :class="wrapperClassName">
<BFormGroup :label="label" :label-for="labelFor">
<BFormInput
v-bind="$attrs"
:min="minValue"
:max="maxValue"
:model-value="modelValue"
:reset-value="props.schemaDescription.default"
:locale="$i18n.locale"
:required="!props.schemaDescription.optional"
@input="updateValue($event.target.value)"
/>
<BFormInvalidFeedback v-if="errorMessage">
{{ props.errorMessage }}
</BFormInvalidFeedback>
</BFormGroup>
</div>
</template>
<script setup>
import { computed } from 'vue'
defineOptions({
inheritAttrs: false
})
const props = defineProps({
errorMessage: {
type: String,
required: false,
},
label: {
type: String,
required: true,
},
modelValue: {
type: String,
required: true,
},
name: {
type: String,
required: true,
},
schemaDescription: {
type: Object,
required: true,
},
})
const emit = defineEmits()
const updateValue = (newValue) => emit('update:modelValue', newValue, props.name)
// extract additional parameter like min and max from schema
const getDateOnly = (rules, name) => rules.find(test => test.name === name)?.params[name]
const rules = props.schemaDescription.tests
const minValue = getDateOnly(rules, 'min')
const maxValue = getDateOnly(rules, 'max')
const wrapperClassName = computed(() => `input-${props.name}`)
const labelFor = computed(() => `${props.name}-input-field`)
</script>

View File

@ -94,7 +94,7 @@ const form = ref({
id: null,
date: '',
memo: '',
hours: 0,
hours: 0.0,
amount: '',
})
const originalContributionDate = ref('')

View File

@ -0,0 +1,15 @@
import {object, string, date } from 'yup'
export const createContributionFormValidation = (t) => {
return object({
// The date field is required and needs to be a valid date
// contribution date
date:
date()
.required(t('contribution.noDateSelected'))
.min((new Date(new Date().setMonth(new Date().getMonth() - 1, 1))).toISOString().slice(0,10)) // min date is first day of last month
.max(new Date().toISOString().slice(0,10))
.default(''), // date cannot be in the future
memo: string().required(t('')).min(5).max(255)
})
}

View File

@ -1657,14 +1657,13 @@
dependencies:
vee-validate "4.14.7"
"@vee-validate/yup@^4.14.1":
version "4.14.7"
resolved "https://registry.yarnpkg.com/@vee-validate/yup/-/yup-4.14.7.tgz#a029151394ae4fbc7a038dbb49acc86f2ba78ddc"
integrity sha512-sMLkSXbVWIFK0BE8gEp2Gcdd3aqpTggBjbkrYmcdgyHBeYoPmhBHhUpkXDFhmsckie2xv6lNTicGO5oJt71N1Q==
"@vee-validate/yup@^4.15.0":
version "4.15.0"
resolved "https://registry.yarnpkg.com/@vee-validate/yup/-/yup-4.15.0.tgz#409f9b57414fadd5b86bc6ada18cd51a7ccd121c"
integrity sha512-paK2ZdxZJRrUGwqaqf7KMNC+n5C7UGs7DofK7wZCza/zKT/QtFSxVYgopGoYYrbAfd6DpVmNpf/ouBuRdPBthA==
dependencies:
type-fest "^4.8.3"
vee-validate "4.14.7"
yup "^1.3.2"
vee-validate "4.15.0"
"@vitejs/plugin-vue@5.1.4":
version "5.1.4"
@ -7133,6 +7132,14 @@ vee-validate@4.14.7, vee-validate@^4.13.2:
"@vue/devtools-api" "^7.5.2"
type-fest "^4.8.3"
vee-validate@4.15.0:
version "4.15.0"
resolved "https://registry.yarnpkg.com/vee-validate/-/vee-validate-4.15.0.tgz#eb77a9c867669d34abbc33ca5e16f2a991eb7ad5"
integrity sha512-PGJh1QCFwCBjbHu5aN6vB8macYVWrajbDvgo1Y/8fz9n/RVIkLmZCJDpUgu7+mUmCOPMxeyq7vXUOhbwAqdXcA==
dependencies:
"@vue/devtools-api" "^7.5.2"
type-fest "^4.8.3"
vite-node@2.1.8:
version "2.1.8"
resolved "https://registry.yarnpkg.com/vite-node/-/vite-node-2.1.8.tgz#9495ca17652f6f7f95ca7c4b568a235e0c8dbac5"
@ -7518,7 +7525,7 @@ yocto-queue@^0.1.0:
resolved "https://registry.yarnpkg.com/yocto-queue/-/yocto-queue-0.1.0.tgz#0294eb3dee05028d31ee1a5fa2c556a6aaf10a1b"
integrity sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q==
yup@^1.3.2, yup@^1.4.0:
yup@^1.6.1:
version "1.6.1"
resolved "https://registry.yarnpkg.com/yup/-/yup-1.6.1.tgz#8defcff9daaf9feac178029c0e13b616563ada4b"
integrity sha512-JED8pB50qbA4FOkDol0bYF/p60qSEDQqBD0/qeIrUCG1KbPBIQ776fCUNb9ldbPcSTxA69g/47XTo4TqWiuXOA==