appsettings.json: >
Код: Выделить всё
{
"Logging": {
"LogLevel": {
"Default": "Information",
"Microsoft.AspNetCore": "Warning"
}
},
"AllowedHosts": "*",
"Level": "One",
"Levels": [
"One",
"Two",
"Three",
"Four"
],
"MoreLevel":
{
"MoreLevel": "One"
},
"MoreLevels": [
{
"AnotherLevel": "One"
},
{
"MoreLevel": "Two"
},
{
"MoreLevel": "Three"
},
{
"MoreLevel": "Four"
}
]
}
Код: Выделить всё
public enum LevelEnum
{
Zero,
One,
Two,
Three
}
Код: Выделить всё
public class AppOptions
{
[Required]
public LevelEnum? Level { get; set; } = null;
[Required]
[ValidateObjectMembers]
public MoreLevelOptions? MoreLevel { get; set; } = null;
[Required]
[ValidateObjectMembers]
public List? Levels { get; set; } = null;
[Required]
[ValidateObjectMembers]
public List? MoreLevels { get; set; } = null;
}
Код: Выделить всё
public class MoreLevelOptions
{
[Required]
public LevelEnum? MoreLevel { get; set; } = null;
}
Код: Выделить всё
public static void Main(string[] args)
{
var builder = WebApplication.CreateBuilder(args);
// Binding configuration
builder.Services
.AddOptions()
.Bind(builder.Configuration)
.ValidateDataAnnotations()
.ValidateOnStart();
// Getting 'root' configuration
AppOptions config = builder.Configuration.Get();
// Building app
var app = builder.Build();
// Runnin app
app.Run();
}
Неверное имя перечисления
Использование «Уровень»: «Один» при проверке appsetting.json работает нормально.
При использовании значения «Уровень»: «Четыре» я получаю исключение:
Код: Выделить всё
System.InvalidOperationException: 'Failed to convert configuration value at 'Level' to type 'NET8Validation.LevelEnum'.'
FormatException: Four is not a valid value for LevelEnum.
ArgumentException: Requested value 'Four' was not found.
Хорошо, все работает так, как ожидалось, но я получаю исключение не на .Bind(), но вместо этого, когда я пытаюсь .Get() настроить и сопоставить ее с моделью AppConfig.
ОК , я предпочитаю иметь подтверждение в момент .Bind(), но это так..
[Обязательный] атрибут
Если в appsettings.json я переключусь с
Код: Выделить всё
"Level": "One"
Код: Выделить всё
"NewLevel": "One"
Только при выполнении самой последней строки app.Run(); я получаю исключение:
Код: Выделить всё
'DataAnnotation validation failed for 'AppOptions' members: 'Level' with the error: 'The Level field is required.'.'
Почему анализ перечисления и [Обязательная] проверка выполняются в разное время в процессе запуска приложения?
Неверное имя перечисления в перечислении массив
Просмотр раздела appsettings.json
Код: Выделить всё
"Levels": [
"One",
"Two",
"Three",
"Four"
]
Код: Выделить всё
FormatException: Four is not a valid value for LevelEnum
Почему я получаю FormatException, как в первом случае? Почему я в итоге получаю 3 элемента в полях Level, а 1-й элемент вместо исключения просто отбрасывается?
Похоже, что валидация с полями работает по-другому и массивы, я ошибаюсь?
[Обязательно] в поле объекта (класса)
Имейте в виду, что
Код: Выделить всё
public class AppOptions
{
..
[Required]
[ValidateObjectMembers]
public MoreLevelOptions? MoreLevel { get; set; } = null;
..
}
Код: Выделить всё
public class MoreLevelOptions
{
[Required]
public LevelEnum? MoreLevel { get; set; } = null;
}
Если в appsettings.json я переключаюсь с
Код: Выделить всё
"MoreLevel":
{
"MoreLevel": "One"
}
Код: Выделить всё
"MoreLevel":
{
"AnotherLevel": "One"
}
Теперь мне действительно нужно декорировать поля всех объектов (классов) в модели(ах) appsettings.json, принудительно проверить все листья дерева?
Неверное имя перечисления в массиве классов
Просмотр раздела appsettings.json, сопоставленного с помощью List ? MoreLevels {получить; набор; } = null; поле
Код: Выделить всё
"MoreLevels": [
{
"AnotherLevel": "One"
},
{
"MoreLevel": "Two"
},
{
"MoreLevel": "Three"
},
{
"MoreLevel": "Four"
}
]
code> значение в 4-м элементе.
Я не получаю никаких исключений, ни для 1-го элемента (
Код: Выделить всё
MoreLevelТеперь, как я могу получить исключения для этого те же самые условия уже протестированы и работают в плоских полях (а не внутри полей объекта)?
Выводы
Мне очень трудно понять, как происходит валидация. «из коробки» работает. Моя цель должна состоять в том, чтобы украсить необходимые поля внутри классов модели параметров атрибутами [Required] и другими аннотациями данных, а также в одном месте вызвать .Bind() или .Get() методы и быть уверенным, что все проверки проверяются по всем оформленным полям моей модели(-й).
Кроме того, пользовательские Атрибуты проверки, которые я мог бы унаследовать от [ValidationAttribute], кажется, никогда не срабатывают, ни в .Bind(), ни в .Get(), ни в .Run() время.
Итак... как я могу просто заставить проверку конфигурации работать так, как я ожидаю?
Подробнее здесь: https://stackoverflow.com/questions/778 ... nnotations
Мобильная версия