Verbose режим

Под verbose-режимом в контексте Joi обычно понимается максимальная детализация информации о процессе валидации: расширенные сообщения об ошибках, полное раскрытие структуры ошибок, контекста, путей данных, а также подробное описание самой схемы через механизмы introspection. В Joi отсутствует отдельный переключатель с названием «verbose», однако аналогичный эффект достигается через комбинацию API возможностей: конфигурацию валидации, работу с объектом ошибки, настройку сообщений и использование метода описания схемы.


Структура результата валидации и уровень детализации

При вызове schema.validate(value, options) или schema.validateAsync(value, options) возвращается объект, содержащий:

  • value — преобразованное и валидированное значение
  • error — объект ошибки ValidationError, если валидация не прошла
  • warning — предупреждения (при соответствующих настройках)

Максимально подробное представление ошибок формируется внутри error.details.

Каждый элемент массива details содержит:

  • message — итоговое сообщение ошибки
  • path — путь к некорректному полю (массив ключей)
  • type — тип нарушения правила (например, string.min, number.base)
  • context — контекст ошибки (ожидаемое значение, лимиты, метаданные)
  • original — исходное значение (в зависимости от версии и настроек)
  • state — внутреннее состояние парсинга (используется для отладки цепочек)

Именно структура details является основой verbose-представления ошибок, позволяя анализировать не только факт сбоя, но и его точное происхождение.


Управление полнотой ошибок: abortEarly и накопление результатов

Одним из ключевых механизмов детализации является параметр:

  • abortEarly: false

По умолчанию Joi прекращает проверку при первой ошибке. Это уменьшает объем информации. При отключении раннего прерывания формируется полный список всех нарушений.

Пример логики:

  • abortEarly: true — одна ошибка
  • abortEarly: false — полный массив всех найденных несоответствий

При использовании verbose-подхода почти всегда включается накопление ошибок, поскольку оно раскрывает полную картину состояния данных.


Глубокая структура ValidationError

Объект ValidationError в Joi содержит дополнительные поля:

  • name — тип ошибки (ValidationError)
  • message — агрегированное сообщение
  • details — массив детальных ошибок
  • annotate() — метод генерации читаемого представления схемы с пометками ошибок
  • isJoi — маркер принадлежности к Joi
  • stack — стек вызовов (при включённой детализации окружения)

Метод annotate() особенно важен для verbose-анализа. Он накладывает ошибки на текстовое описание схемы, позволяя видеть проблемные узлы прямо в структуре.


Метод describe(): verbose-представление схемы

Для анализа самой схемы, а не результата валидации, используется:

  • schema.describe()

Этот метод возвращает структурированное описание схемы в виде объекта, содержащего:

  • тип (type)
  • правила (rules)
  • метки (flags)
  • вложенные структуры (keys, items)
  • альтернативы (alternatives)

Пример логики описания:

  • строка с ограничениями длины
  • число с диапазоном
  • объект с вложенными схемами

describe() используется как основной инструмент introspection и фактически представляет verbose-режим схемы Joi.


Расширение детализации через кастомные сообщения

Уровень информативности ошибок может существенно увеличиваться за счёт кастомных сообщений:

Joi.string().min(5).messages({
  'string.min': 'Значение меньше минимальной длины',
  'string.base': 'Ожидается строка'
})

Каждое правило Joi имеет идентификатор типа ошибки. Подмена сообщений позволяет:

  • сделать ошибки более предметными
  • добавить доменную терминологию
  • устранить абстрактность стандартных формулировок

В verbose-подходе кастомизация сообщений является стандартной практикой, поскольку дефолтные тексты Joi ориентированы на универсальность, а не на прикладной контекст.


Контекст ошибки и диагностическая информация

Поле context в деталях ошибки играет ключевую роль в диагностике. В зависимости от типа правила оно может содержать:

  • limit — ограничение (например, минимум длины)
  • value — фактическое значение
  • key — имя поля
  • label — человекочитаемое имя
  • pattern — регулярное выражение
  • peers — связанные поля (для object rules)

Эта информация позволяет точно реконструировать причину нарушения без необходимости дополнительной обработки входных данных.


Путь ошибки (path) и вложенные структуры

Joi активно используется для валидации вложенных объектов и массивов. В verbose-режиме особое значение имеет поле path, представляющее маршрут до проблемного значения:

Примеры:

  • ["user", "email"]
  • ["items", 3, "price"]
  • ["profile", "addresses", 0, "zip"]

path позволяет:

  • локализовать ошибку в глубоко вложенных структурах
  • строить UI-валидацию форм
  • агрегировать ошибки по секциям

Множественные ошибки и агрегация результата

При отключённом abortEarly формируется полный список ошибок, однако Joi дополнительно группирует их в массив details, не выполняя иерархическую агрегацию по умолчанию.

Каждая ошибка независима, но содержит собственный path, что позволяет восстанавливать структуру вручную при необходимости построения сложных диагностических отчётов.


Режим преобразования и влияние на детализацию

Опция:

  • convert: true

влияет на предварительную нормализацию данных перед валидацией.

В verbose-контексте это важно, поскольку:

  • ошибки могут возникать уже после преобразования типов
  • исходные данные и преобразованные значения могут различаться
  • контекст ошибки отражает пост-обработанное состояние

При convert: false увеличивается предсказуемость, но уменьшается гибкость обработки входных данных.


Прозрачность альтернатив и сложных схем

При использовании alternatives() Joi формирует ветвящиеся схемы. В verbose-режиме ошибки содержат информацию о:

  • неудачных ветках
  • причинах отклонения альтернатив
  • контексте выбора схемы

Это особенно важно при:

  • условной валидации
  • схемах с зависимостями полей
  • динамических структурах данных

Расширенные режимы вывода ошибок

Joi поддерживает тонкую настройку через prefs:

  • errors.wrap.label
  • errors.language
  • errors.escapeHtml
  • messages

Конфигурация:

const schema = Joi.object({...}).prefs({
  errors: {
    label: 'key'
  }
})

Эти параметры влияют на то, насколько «развёрнутым» будет итоговое сообщение.


Детализация через стек и отладочную информацию

При включённой отладочной конфигурации могут быть доступны:

  • stack trace
  • внутренние переходы валидатора
  • состояние правил

Хотя стек не является частью стандартного verbose-вывода, он используется при глубокой диагностике сложных схем и нестабильных данных.


Формирование человекочитаемого отчёта через annotate()

Метод:

  • error.annotate()

создаёт текстовое представление схемы с встраиванием ошибок прямо в структуру.

Принцип:

  • схема превращается в строковое дерево
  • проблемные узлы помечаются текстовыми маркерами
  • сохраняется иерархия вложенности

Это один из наиболее наглядных способов verbose-анализа, особенно при отладке сложных object-схем.


Поведение при асинхронной валидации

validateAsync возвращает промис, но структура ошибки идентична синхронной версии. Verbose-детализация сохраняется полностью, включая:

  • details
  • context
  • path

Асинхронность влияет только на способ получения результата, но не на глубину информации.