Skip to content

nixel2007/validate

Repository files navigation

validate

Тестирование Quality Gate Coverage

Валидация объектов на основе правил-аннотаций для OneScript.

Библиотека позволяет описывать ограничения прямо на свойствах объектов через аннотации и выполнять проверку одним вызовом валидатора. Поддерживается проверка вложенных объектов, настраиваемые сообщения и простое расширение набора правил.

Для навигации по коллекциям используйте переключающую аннотацию &ДляКаждого:

  • &ДляКаждого("Значение") — переключает контекст на элементы коллекции (значение режима можно опустить)
  • &ДляКаждого("Ключ") — переключает контекст на ключи коллекции (только для коллекций, итерируемых как КлючИЗначение)

Требования

  • OneScript 1.9.2 или выше

Установка

  • Через OPM (OneScript Package Manager):
opm install validate
  • Локально в проект: добавьте зависимость в ваш packagedef:
    .ЗависитОт("validate", "0.1.0")

Быстрый старт

Опишите ограничения аннотациями на полях вашего объекта:

&Заполнено(Сообщение = "Произвольное сообщение")
Перем Поле1 Экспорт;

&Заполнено
Перем Поле2 Экспорт;

&Минимум(-10)
&Максимум(10)
Перем Поле3 Экспорт;

&Валидно
Перем ВложенныйОбъект Экспорт;

&Тип("Число")
Перем Поле4 Экспорт;

// Элементы массива — строки
&Тип("Массив")
&ДляКаждого
&Тип("Строка")
Перем КоллекцияСтрок Экспорт;

// Значения структуры — числа
&Тип("Структура")
&ДляКаждого
&Тип("Число")
Перем СтруктураЧисел Экспорт;

// Ключи соответствия — числа
&Тип("Соответствие")
&ДляКаждого("Ключ")
&Тип("Число")
Перем СоответствиеЧисловыхКлючей Экспорт;

Выполните валидацию и выведите ошибки:

Валидатор = Новый Валидатор;
Объект = Новый ТестовыйОбъект; // ваш класс с аннотациями

Результат = Валидатор.Валидировать(Объект);
Если Результат.Количество() > 0 Тогда
		Сообщить(Валидатор.ОписаниеОшибокВалидации(Результат));
КонецЕсли;

Пример строки в отчете об ошибках:

[filled]: Объект: <ТипОбъекта>, Свойство: Поле2, Сообщение: Значение не заполнено

Подробные примеры работы с Валидатором

Пример 1: Создание класса с аннотациями

Создайте класс с аннотациями валидации:

// Класс ПользовательДанные.os

&Заполнено(Сообщение = "Имя пользователя обязательно для заполнения")
Перем Имя Экспорт;

&Заполнено
&Минимум(18)
&Максимум(120)
Перем Возраст Экспорт;

&Заполнено
Перем Email Экспорт;

&Минимум(0)
&Максимум(100000)
Перем Зарплата Экспорт;

&Истина
Перем Активен Экспорт;

Пример 2: Валидация данных (корректных и некорректных)

// Создаем валидатор
Валидатор = Новый Валидатор;

// Сначала валидируем корректные данные
Пользователь = Новый ПользовательДанные;
Пользователь.Имя = "Иван Иванов";
Пользователь.Возраст = 30;
Пользователь.Email = "ivan@example.com";
Пользователь.Зарплата = 50000;
Пользователь.Активен = Истина;

РезультатВалидации = Валидатор.Валидировать(Пользователь);

// Проверяем результат - для корректных данных ошибок не будет
Если РезультатВалидации.Количество() = 0 Тогда
    Сообщить("Данные корректны! Валидация прошла успешно.");
Иначе
    Сообщить("Неожиданные ошибки при валидации корректных данных");
КонецЕсли;

// Теперь валидируем некорректные данные
НекорректныйПользователь = Новый ПользовательДанные;
НекорректныйПользователь.Имя = ""; // Пустое имя
НекорректныйПользователь.Возраст = 15; // Меньше минимума
НекорректныйПользователь.Зарплата = 150000; // Больше максимума
НекорректныйПользователь.Активен = Ложь; // Должно быть Истина

РезультатВалидации = Валидатор.Валидировать(НекорректныйПользователь);

// Выводим все ошибки
Если РезультатВалидации.Количество() > 0 Тогда
    Сообщить("Найдено нарушений: " + РезультатВалидации.Количество());
    Сообщить(Валидатор.ОписаниеОшибокВалидации(РезультатВалидации));
Иначе
    Сообщить("Ошибка: валидация должна была найти нарушения");
КонецЕсли;

Пример 3: Обработка отдельных нарушений

// Создаем объект с ошибками
Пользователь = Новый ПользовательДанные;
Пользователь.Возраст = 200; // Превышает максимум
// Остальные поля не заполнены

РезультатВалидации = Валидатор.Валидировать(Пользователь);

// Обрабатываем каждое нарушение отдельно
Для Каждого Нарушение Из РезультатВалидации Цикл
    
    ИмяСвойства = Нарушение.ИмяСвойства();
    Сообщение = Нарушение.Сообщение();
    КодОшибки = Нарушение.Код();
    
    // Можно обрабатывать разные типы ошибок по-разному
    Если КодОшибки = "filled" Тогда
        Сообщить("Поле не заполнено: " + ИмяСвойства + " - " + Сообщение);
    ИначеЕсли КодОшибки = "max" Тогда
        Сообщить("Превышен максимум для поля: " + ИмяСвойства + " - " + Сообщение);
    ИначеЕсли КодОшибки = "min" Тогда
        Сообщить("Значение меньше минимума для поля: " + ИмяСвойства + " - " + Сообщение);
    Иначе
        Сообщить("Ошибка валидации [" + КодОшибки + "]: " + ИмяСвойства + " - " + Сообщение);
    КонецЕсли;
    
КонецЦикла;

Пример 4: Валидация вложенных объектов

// Класс ПользовательДанные.os (сокращенная версия)
&Заполнено
Перем Имя Экспорт;

&Валидно  // Эта аннотация указывает, что нужно валидировать вложенный объект
Перем Адрес Экспорт;

// Класс Адрес.os
&Заполнено
Перем Город Экспорт;

&Заполнено
&Минимум(100000)
&Максимум(999999)
Перем Индекс Экспорт;

// Создаем пользователя с адресом
Пользователь = Новый ПользовательДанные;
Пользователь.Имя = "Петр Петров";

// Создаем адрес с ошибкой
Адрес = Новый Адрес;
Адрес.Город = "Москва";
Адрес.Индекс = 12345; // Меньше минимума

Пользователь.Адрес = Адрес;

// Валидация проверит и основной объект, и вложенный
// благодаря аннотации &Валидно у поля Адрес
РезультатВалидации = Валидатор.Валидировать(Пользователь);

Если РезультатВалидации.Количество() > 0 Тогда
    Сообщить("Ошибки валидации:");
    Сообщить(Валидатор.ОписаниеОшибокВалидации(РезультатВалидации));
КонецЕсли;

Поддерживаемые аннотации

  • &Заполнено(Сообщение = "...") — значение поля должно быть заполнено. Код нарушения: filled.
  • &Истина — булево значение должно быть Истина. Код нарушения: true.
  • &Ложь — булево значение должно быть Ложь. Код нарушения: false.
  • &Минимум(<число>) — значение не меньше минимума. Код нарушения: min.
  • &Максимум(<число>) — значение не больше максимума. Код нарушения: max.
  • &Тип(<строка>) — значение должно иметь указанный тип. Код нарушения: type.
  • &Валидно — рекурсивная проверка вложенного объекта. Код нарушения: valid.

Переключение контекста коллекций задаётся аннотацией &ДляКаждого; её можно указывать несколько раз для вложенных коллекций.

Сообщение об ошибке можно переопределить параметром аннотации Сообщение.

Примеры для коллекций

  • Элементы массива в диапазоне 0..10:
&Тип("Массив")
&ДляКаждого
&Тип("Число")
&Минимум(0)
&Максимум(10)
Перем МассивЧиселСДиапазоном Экспорт;
  • Ключи соответствия больше 5 (минимум 6):
&Тип("Соответствие")
&ДляКаждого("Ключ")
&Тип("Число")
&Минимум(6)
Перем СоответствиеКлючиБольше5 Экспорт;

Примечание: при &ДляКаждого("Ключ") для коллекций без ключей (например, Массив) будет выброшено исключение.

Расширение и кастомизация

  • Конструктор валидатора поддерживает подмену фабрики валидаций и контейнера аннотаций:
Валидатор = Новый Валидатор(МояФабрикаВалидаций, МойКонтейнерАннотаций);
  • По умолчанию используется СтандартнаяФабрикаВалидаций, где назначено соответствие аннотаций и классов валидаций (ВалидацияОграниченияЗаполнено, ...Минимум, ...Максимум, ...Истина, ...Ложь, ...Тип, ...Валидно).
  • Можно добавлять собственные аннотации в контейнер и свои реализации классов валидаций/ограничений.

Запуск тестов

В проект включены авто-тесты на 1testrunner. Запустить можно так:

oscript tasks/test.os

Результаты в формате JUnit сохраняются в каталоге out.

Покрытие кода

Для прогона тестов со сбором покрытия используйте задачу из tasks/coverage.os:

oscript tasks/coverage.os

Скрипт сохранит статистику в out/stat.json и сформирует отчеты:

  • out/genericCoverage.xml — Generic Coverage (используется Sonar)
  • out/cobertura.xml — отчет в формате Cobertura (используется плагином Coverage Gutters в VSCode)

Лицензия

Этот проект лицензируется под лицензией MIT. Подробности см. в файле LICENSE.md.

About

No description or website provided.

Topics

Resources

License

Stars

Watchers

Forks

Packages

 
 
 

Contributors