Формы валидируются на Regle — тайп-сейф headless-библиотеке для Vue 3 (модуль Regle для Nuxt). useRegle и обёртки withMessage/withAsync/withParams — автоимпорты; правила — из набора Regle rules.
Мост между Regle и core-формами — композабл useFormField: разворачивает статус поля r$ в плоское состояние error/invalid/pending/dirty. Ошибка идёт единственным каналом — prop error контрола; CoreFormGroup получает только label/hint/required.
Текст ошибки рендерит контрол (role="alert" + aria-invalid); если передать error ещё и в CoreFormGroup, ошибка задвоится и скринридер озвучит её дважды. describedBy из слота группы связывает контрол с активным пояснением — всегда прокидывайте его в контрол.
Чистое поле не орёт ошибкой на первый рендер. Ошибки появляются у правленых (dirty) полей или все сразу после r$.$validate(). $pending — тихий статус: сабмит блокируется через :loading кнопки, спиннер на поле не показывается.
Сообщения required/email/minLength/maxLength уже локализованы глобально (app/regle-config.ts, ключи validation.*). Сообщение кастомного правила — на месте использования через withMessage(rule, t('…')). У поля с async-правилом Regle дебаунсит ввод на 200 мс — проверка запускается после остановки ввода.
Секции «Валидация через Regle» — в песочницах:
CoreInputCoreFormGroup