Вещи, Которые Я Делаю в Каждом Проекте .NET. Продолжение
1-2
3
4. Задаём авторизацию глобально
Если вы используете, например, контроллеры, вам нужно не забыть добавить атрибут Authorize во всех контроллерах и действиях, которые вы хотите защитить (а это обычно большинство). Либо нужно не забыть наследовать от какого-нибудь базового контроллера, у которого есть этот атрибут. Но проблема в том, что если вы забудете, то этот метод/контроллер полностью открыты для внешнего мира.
Решение этой проблемы — так называемая резервная политика (FallbackPolicy) в ASP.NET Core. Резервная политика работает так: если вы не укажете другую политику, эта будет срабатывать каждый раз. В контейнере DI вы просто добавляете авторизацию и устанавливаете эту резервную политику:
bulder.Services.AddAuthorization(opts =>
{
opts.FallbackPolicy = new
AuthorizationPolicyBuilder()
.RequireAuthenticatedUser()
.Build();
});
Вы можете создать любую политику, но проще использовать конструктор политик авторизации и запросить аутентифицированного пользователя. Это сработает только в том случае, если вы не укажете ничего другого в контроллере. Если в контроллер или метод контроллера вы добавите атрибут AllowAnonymous, либо атрибут с более строгой политикой, будет использован он. А так вы защищены по умолчанию.
5. Валидация
Наверное, большинство из вас использовали аннотации данных для валидации. Проблема с ними в том, что, если нужно наложить несколько условий на свойство, добавление аннотации для каждого условия быстро становится громоздким и загружает модель. Не говоря уже о случае, когда нам требуется какая-то нестандартная валидация. Кроме того, для них сложно писать автоматизированные тесты.
Fluent Validation позволяет создавать бизнес-правила, которые легко читать даже бизнесу. Их также легко тестировать. Сложные правила создавать тоже просто. Например, в США, вы не можете пользоваться медицинской страховкой родителей после 26 лет. И вот правило для этого:
public class InsuranceValidator
: AbstractValidator<Insurance>
{
public InsuranceValidator()
{
RuleFor(model => model.Age)
.Must(age => age < 26)
.When(model => model.IsDependent)
.WithMessage(“A dependent must be younger than 26”);
}
}
Вы можете показать это бизнесу, и они поймут эти условия, даже не зная кода.
6. Заголовки сервера
По умолчанию ASP.NET Core в ответ добавляет HTTP-заголовок с именем сервера. Если вы используете Kestrel, это значение будет Kestrel. Зачем он это делает? Скорей всего, в Microsoft просто хотят знать, сколько сайтов используют ASP.NET Core. В .NET Framework было ещё хуже, потому что выдавались и версии MVC и .NET. Но это раскрывает хакерам, что вы используете. Т.е. им не нужно проверять ваш сайт на уязвимости Java или Python, только на уязвимости, специфичные для .NET. Удаление заголовка не избавит вас от атак, но увеличит количество времени, которое атакующий потратит. Если у вас есть публичный веб-сайт, он гарантированно подвергался различным атакам. Удалить заголовок легко, просто добавьте эту строку:
builder.WebHost.UseKestrel(opts => opts.AddServerHeader = false);
Продолжение следует…
Источник: https://youtu.be/SvcRvolP2NE