Skip to content

Commit

Permalink
F #6662: Fix form validation (#3201)
Browse files Browse the repository at this point in the history
* Include field path for ALL form errors
* Fix VNC validation

Signed-off-by: Victor Hansson <vhansson@opennebula.io>
  • Loading branch information
vichansson authored Aug 15, 2024
1 parent 7d09405 commit a7da395
Show file tree
Hide file tree
Showing 4 changed files with 55 additions and 89 deletions.
19 changes: 9 additions & 10 deletions src/fireedge/src/client/components/FormStepper/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,13 @@ import {
import CustomMobileStepper from 'client/components/FormStepper/MobileStepper'
import CustomStepper from 'client/components/FormStepper/Stepper'
import SkeletonStepsForm from 'client/components/FormStepper/Skeleton'
import { groupBy, Step, StepsForm, isDevelopment } from 'client/utils'
import {
groupBy,
Step,
StepsForm,
isDevelopment,
deepStringify,
} from 'client/utils'
import { T } from 'client/constants'
import get from 'lodash.get'
import { set, isEmpty } from 'lodash'
Expand Down Expand Up @@ -208,15 +214,8 @@ const FormStepper = ({

const setErrors = ({ inner = [], message = { word: 'Error' } } = {}) => {
const errorsByPath = groupBy(inner, 'path') ?? {}
const totalErrors = Object.values(errorsByPath).reduce((count, value) => {
if (Array.isArray(value)) {
const filteredValue = value?.filter(Boolean) || []

return count + filteredValue?.length || 0
}

return count
}, 0)
const jsonErrorsByPath = deepStringify(errorsByPath, 6) || ''
const totalErrors = (jsonErrorsByPath.match(/\bmessage\b/g) || []).length

const translationError =
totalErrors > 0 ? [T.ErrorsOcurred, totalErrors] : Object.values(message)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -77,7 +77,7 @@ export const TYPE = (isUpdate) => ({
.test('is-valid-type', 'Invalid value', function (value) {
if (
typeof value === 'boolean' ||
value === 'VNC' ||
value?.toUpperCase() === 'VNC' ||
value === undefined
) {
return true
Expand Down
8 changes: 6 additions & 2 deletions src/fireedge/src/client/utils/helpers.js
Original file line number Diff line number Diff line change
Expand Up @@ -559,9 +559,13 @@ export const deepStringify = (obj, depth = 3) => {
.map(
([key, value]) =>
`${key?.toString() ?? 'UNDEFINED'}:${
typeof value === 'object'
Array.isArray(value)
? `[${value
.map((item) => deepStringify(item, depth - 1))
.join(',')}]`
: typeof value === 'object'
? deepStringify(value, depth - 1)
: value?.toString() ?? 'UNDEFINED'
: _.toString(value) ?? 'UNDEFINED'
}`
)
.join(',')
Expand Down
115 changes: 39 additions & 76 deletions src/fireedge/src/client/utils/translation.js
Original file line number Diff line number Diff line change
Expand Up @@ -102,94 +102,57 @@ const buildTranslationLocale = () => {
default: ({ path }) => `${path} ${T['validation.mixed.default']}`,
required: ({ path }) => `${path} ${T['validation.mixed.required']}`,
defined: ({ path }) => `${path} ${T['validation.mixed.defined']}`,
oneOf: ({ values }) => ({ word: T['validation.mixed.oneOf'], values }),
notOneOf: ({ values }) => ({
word: T['validation.mixed.notOneOf'],
values,
}),
notType: ({ type }) =>
T[`validation.mixed.notType.${type}`] ?? T['validation.mixed.notType'],
oneOf: ({ path, values }) =>
`${path} ${T['validation.mixed.oneOf']}: ${values}`,
notOneOf: ({ path, values }) =>
`${path} ${T['validation.mixed.notOneOf']}: ${values}`,
notType: ({ path, type }) =>
`${path} ${
T[`validation.mixed.notType.${type}`] ?? T['validation.mixed.notType']
}`,
},
string: {
length: ({ length }) => ({
word: T['validation.string.length'],
values: length,
}),
min: ({ min }) => ({
word: T['validation.string.min'],
values: min,
}),
max: ({ max }) => ({
word: T['validation.string.max'],
values: max,
}),
matches: ({ matches }) => ({
word: T['validation.string.matches'],
values: matches,
}),
email: () => T['validation.string.email'],
url: () => T['validation.string.url'],
uuid: () => T['validation.string.uuid'],
trim: () => T['validation.string.trim'],
lowercase: () => T['validation.string.lowercase'],
uppercase: () => T['validation.string.uppercase'],
length: ({ path, length }) =>
`${path} ${T['validation.string.length']}: ${length}`,
min: ({ path, min }) => `${path} ${T['validation.string.min']}: ${min}`,
max: ({ path, max }) => `${path} ${T['validation.string.max']}: ${max}`,
matches: ({ path, matches }) =>
`${path} ${T['validation.string.matches']}: ${matches}`,
email: ({ path }) => `${path} ${T['validation.string.email']}`,
url: ({ path }) => `${path} ${T['validation.string.url']}`,
uuid: ({ path }) => `${path} ${T['validation.string.uuid']}`,
trim: ({ path }) => `${path} ${T['validation.string.trim']}`,
lowercase: ({ path }) => `${path} ${T['validation.string.lowercase']}`,
uppercase: ({ path }) => `${path} ${T['validation.string.uppercase']}`,
},
number: {
min: ({ min }) => ({
word: T['validation.number.min'],
values: min,
}),
max: ({ max }) => ({
word: T['validation.number.max'],
values: max,
}),
lessThan: ({ less }) => ({
word: T['validation.number.lessThan'],
values: less,
}),
moreThan: ({ more }) => ({
word: T['validation.number.moreThan'],
values: more,
}),
positive: () => T['validation.number.positive'],
negative: () => T['validation.number.negative'],
integer: () => T['validation.number.integer'],
min: ({ path, min }) => `${path} ${T['validation.number.min']}: ${min}`,
max: ({ path, max }) => `${path} ${T['validation.number.max']}: ${max}`,
lessThan: ({ path, less }) =>
`${path} ${T['validation.number.lessThan']}: ${less}`,
moreThan: ({ path, more }) =>
`${path} ${T['validation.number.moreThan']}: ${more}`,
positive: ({ path }) => `${path} ${T['validation.number.positive']}`,
negative: ({ path }) => `${path} ${T['validation.number.negative']}`,
integer: ({ path }) => `${path} ${T['validation.number.integer']}`,
},
boolean: {
isValue: ({ value }) => ({
word: T['validation.boolean.isValue'],
values: [value],
}),
isValue: ({ path, value }) =>
`${path} ${T['validation.boolean.isValue']}: ${value}`,
},
date: {
min: ({ min }) => ({
word: T['validation.date.min'],
values: min,
}),
max: ({ max }) => ({
word: T['validation.date.max'],
values: max,
}),
min: ({ path, min }) => `${path} ${T['validation.date.min']}: ${min}`,
max: ({ path, max }) => `${path} ${T['validation.date.max']}: ${max}`,
},
object: {
noUnknown: ({ nounknown }) => ({
word: T['validation.object.noUnknown'],
values: nounknown,
}),
noUnknown: ({ path, nounknown }) =>
`${path} ${T['validation.object.noUnknown']}: ${nounknown}`,
},
array: {
min: ({ min }) => ({
word: T['validation.array.min'],
values: min,
}),
max: ({ max }) => ({
word: T['validation.array.max'],
values: max,
}),
length: ({ length }) => ({
word: T['validation.array.length'],
values: length,
}),
min: ({ path, min }) => `${path} ${T['validation.array.min']}: ${min}`,
max: ({ path, max }) => `${path} ${T['validation.array.max']}: ${max}`,
length: ({ path, length }) =>
`${path} ${T['validation.array.length']}: ${length}`,
},
})
}
Expand Down

0 comments on commit a7da395

Please sign in to comment.