Skip to content

Commit

Permalink
Merge a47178b into a21c154
Browse files Browse the repository at this point in the history
  • Loading branch information
berdyshev committed Sep 10, 2018
2 parents a21c154 + a47178b commit d925f27
Show file tree
Hide file tree
Showing 4 changed files with 74 additions and 44 deletions.
10 changes: 8 additions & 2 deletions src/layouts/Layout.js
Original file line number Diff line number Diff line change
Expand Up @@ -28,9 +28,15 @@ export class LayoutField {
validate(value) {
if (Array.isArray(this.validation) && this.validation.length) {
for (let i = 0; i < this.validation.length; i++) {
const [ruleName, ...args] = this.validation[i].split(':');
const validationDef = this.validation[i];
let rule = validationDef;
let message;
if (typeof validationDef === 'object') {
({ rule, message } = validationDef);
}
const [ruleName, ...args] = rule.split(':');
if (ruleName in validations) {
const error = validations[ruleName](value, ...args);
const error = validations[ruleName](value, args, message);
if (error) {
return error;
}
Expand Down
24 changes: 20 additions & 4 deletions src/layouts/schema.json
Original file line number Diff line number Diff line change
Expand Up @@ -60,7 +60,24 @@
"validation": {
"type": "array",
"items": {
"type": "string"
"oneOf": [{
"type": "object",
"properties": {
"rule": {
"type": "string"
},
"message": {
"type": "string"
}
},
"required": [
"name"
]
},
{
"type": "string"
}
]
}
}
},
Expand Down Expand Up @@ -172,8 +189,7 @@
"title": "Rule"
},
"DefaultValue": {
"anyOf": [
{
"anyOf": [{
"type": "array",
"items": {
"type": "integer"
Expand All @@ -186,4 +202,4 @@
"title": "DefaultValue"
}
}
}
}
66 changes: 28 additions & 38 deletions src/layouts/validations.js
Original file line number Diff line number Diff line change
@@ -1,79 +1,69 @@
import moment from 'moment';

export const required = (value) => {
let message;
if (!value) {
message = 'Field is required';
const formatError = (message, params) => {
if (typeof message === 'string') {
return message.replace(/\{\s*(\w+)\s*\}/g, (_, key) => params[key]);
}
return message;
};

export const min = (value, minValue) => {
let message;
if (value && value < minValue) {
message = `Value should be greater then ${minValue}`;
}
return message;
};
export const required = (value, _, message = 'Field is required') => !value && formatError(message, { value });

export const max = (value, maxValue) => {
let message;
if (value && value > maxValue) {
message = `Value should be less then ${maxValue}`;
}
return message;
};
export const min = (value, [minValue], message = 'Value should be greater then {minValue}') =>
value && value < minValue && formatError(message, { value, minValue });

export const maxLength = (value, lengthValue) => {
export const max = (value, [maxValue], message = 'Value should be less then {maxValue}') =>
value && value > maxValue && formatError(message, { value, maxValue });

export const maxLength = (value, [lengthValue], defaultMessage) => {
let message;
if (!value) {
return message;
}
if (Array.isArray(value) && value.length > lengthValue) {
message = `You should select maximum ${lengthValue} items`;
message = defaultMessage || 'You should select maximum {lengthValue} items';
} else if (String(value).length > lengthValue) {
message = `You should specify up to ${lengthValue} symbols`;
message = defaultMessage || 'You should specify up to {lengthValue} symbols';
}
return message;
return formatError(message, { value, lengthValue });
};

export const minLength = (value, lengthValue) => {
export const minLength = (value, [lengthValue], defaultMessage) => {
let message;
if (!value) {
return message;
}
if (Array.isArray(value) && value.length < lengthValue) {
message = `You should select at least ${lengthValue} items`;
message = defaultMessage || 'You should select at least {lengthValue} items';
} else if (String(value).length < lengthValue) {
message = `You should specify at least ${lengthValue} symbols`;
message = defaultMessage || 'You should specify at least {lengthValue} symbols';
}
return message;
return formatError(message, { value, lengthValue });
};

export const regex = (value, pattern) => {
let message;
if (value && !new RegExp(pattern).test(String(value))) {
message = `Value does not match the pattern "${pattern}"`;
}
return message;
};
export const regex = (value, [pattern], message = 'Value does not match the pattern "{pattern}"') =>
value && !new RegExp(pattern).test(String(value)) && formatError(message, { value, pattern });

export const dateRange = (value, from, to, ...args) => {
export const dateRange = (value, [from, to, ...args], defaultMessage) => {
let message;
if (!value) {
return message;
}
const params = { value, from, to };
if (from && to) {
if (!moment(value).isBetween(from, to, ...args)) {
message = `Date should be between ${from} and ${to}`;
message = defaultMessage || 'Date should be between {from} and {to}';
}
} else if (to) {
if (!moment(value).isBefore(to, ...args)) {
message = `Date should be before ${to}`;
message = defaultMessage || 'Date should be before {to}';
}
} else if (!moment(value).isAfter(from, ...args)) {
message = `Date should be after ${from || 'now'}`;
message = defaultMessage || 'Date should be after {from}';
if (!from) {
params.from = 'now';
}
}

return message;
return formatError(message, params);
};
18 changes: 18 additions & 0 deletions tests/jest/Layouts/layout.js
Original file line number Diff line number Diff line change
Expand Up @@ -112,4 +112,22 @@ describe('>>> Layout Field validations', () => {
expect(field.validate('2018-10-10')).toBe('Date should be before 2018-01-01');
expect(field.validate('1989-06-04')).toBeUndefined();
});

it('should validate with custom message', () => {
const field = new LayoutField({
name: 'field',
type: 'date',
validation: [{ rule: 'dateRange', message: 'The date should be in a future' }]
});
expect(field.validate('1989-06-04')).toBe('The date should be in a future');
});

it('should validate with custom message containing params', () => {
const field = new LayoutField({
name: 'password',
type: 'password',
validation: [{ rule: 'regex:[0-9A-Za-z]{6,}', message: 'Value "{value}" does not match the pattern "{pattern}"' }]
});
expect(field.validate('some')).toBe('Value "some" does not match the pattern "[0-9A-Za-z]{6,}"');
});
});

0 comments on commit d925f27

Please sign in to comment.