Этот сайт использует файлы cookies. Оставаясь на сайте, Вы соглашаетесь с использованием файлов cookies и принимаете Соглашение об использовании сайта.

Core Identity

Авторизация и аутентификация 3.0

565
565

Авторизация и аутентификация — первое, что требуется наладить практически во всех веб-приложениях, а значит, от этого будет отталкиваться и весь остальной функционал разрабатываемой системы. Уделить этому особое внимание не будет лишним. Данная статья посвящена встроенной системе авторизации и аутентификации в ASP.NET Core Identity, также называемой Identity 3.0.


Введение

Но, прежде чем приступить к основной теме, разберемся с терминологией. Глобально предоставление доступа к ограниченным ресурсам в веб-приложениях проходит в три этапа: идентификации, аутентификации и авторизации.

Идентификация — процесс распознавания субъекта (пользователя, программы, процесса) на основе его идентификатора (имени, логина, номера телефона). Если предоставленный идентификатор существует в системе, идентификация прошла успешно, переходим к аутентификации.

Аутентификация — процедура проверки подлинности. Пользователь, предоставивший логин, должен подтвердить, что он тот, за кого себя принимает, например, с помощью пароля.

И третий этап — авторизация — заключается в проверке прав доступа аутентифицированного субъекта к ресурсу. Субъект считается авторизованным, если ему предоставлены соответствующие права доступа к объектам системы.

Начало

Вся эта функциональность уже реализована для ASP.NET Core — проект с открытым исходным кодом под названием Identity 3.0. Для настройки окружения вам понадобится установить:

  • Visual Studio 2015;
  • Update 3 для VS 2015;
  • .NET Core tools for Visual Studio.

Инструкцию по установке и ссылки можно найти здесь.

Для включения функционала Identity создадим проект ASP.NET Core Web Application по шаблону Web Application и в качестве типа аутентификации выберем Individual User Accounts.

ASP.NET Core Identity
ASP.NET Core Identity

В проект будет добавлен пакет Microsoft.AspNetCore.Identity.EntityFrameworkCore, который будет сохранять данные и схемы в SQL Server для Entity Framework Core.

ASP.NET Core Identity

Также этот пакет можно добавить через NuGet Package Manager.

ASP.NET Core Identity

Или же дописав соответствующие зависимости в файле project.json в узлах dependencies и tools.

ASP.NET Core Identity

После сохранения файла в проект автоматически будут добавлены указанные пакеты. Но в этом случае для работы приложения необходимо будет самому настроить строку подключения и работу с базой данных.

Как это работает

В ходе нехитрых манипуляций по созданию проекта мы получили полностью рабочую систему аутентификации и авторизации. Приложение готово к работе и можно уже зарегистрировать нового пользователя и войти под ним в систему.

В ASP.NET Core за настройку обработки запросов отвечает метод Configure класса Startup. При создании проекта с использованием шаблона по умолчанию в этот метод добавится строка app.UseIdentity () ; отвечающая за аутентификацию для потока запросов, основанную на куки.

ASP.NET Core Identity

Также в метод ConfigureServices этого же класса Startup будут добавлены Identity сервисы.

ASP.NET Core Identity

Это позволит использовать их в приложении с помощью встроенной системы внедрения зависимостей.

Теперь при обработке каждого запроса будет проводиться аутентификация пользователя. А авторизацию будет контролировать атрибут Authorize, который можно добавить перед контроллером и отдельным методом в MVC фреймворке.

ASP.NET Core был сильно изменен по сравнению с прошлыми версиями, не остался в стороне и Identity 3.0. Структура БД для Identity 3.0 имеет следующий вид:

ASP.NET Core Identity

Появились две новые таблицы: AspNetRoleClaims и AspNetUserTokens. Пользователи и роли, как и ранее, представлены классами IdentityUser и IdentityRole соответственно. Но теперь они не наследуются от интерфейсов для пользователей и ролей, что очень удобно. Также появились новые инструменты авторизации — политики.

Политика — это одно или несколько требований, необходимых пройти пользователю для авторизации.

Пример

Пусть для доступа к некоторому ресурсу в приложении пользователь должен иметь российское гражданство. Для начала зарегистрируем политику RussianСitizenship в ConfigureService файла startup.cs:

public void ConfigureServices(IServiceCollection services)
{
    // Add framework services.
    services.AddDbContext<ApplicationDbContext>(options =>
        options.UseSqlServer(Configuration.GetConnectionString("DefaultConnection")));

    services.AddIdentity<ApplicationUser, IdentityRole>()
        .AddEntityFrameworkStores<ApplicationDbContext>()
        .AddDefaultTokenProviders();

    services.AddMvc();

    services.AddAuthorization(options =>
    {
        options.AddPolicy("RussianСitizenship",
            policy => policy.Requirements.Add(new RussianСitizenshipRequirement("Russian Federation")));
    });

    // Add application services.
    services.AddTransient<IEmailSender, AuthMessageSender>();
    services.AddTransient<ISmsSender, AuthMessageSender>();
}

Для регистрации политики мы использовали RussianСitizenshipRequirement в качестве авторизационного требования — параметры данных, которые использует политика для оценки текущего пользователя. В нашем случае есть лишь один параметр — гражданство. Для создания требования нужно реализовать интерфейс IAuthorizationRequirement:

public class RussianСitizenshipRequirement : IAuthorizationRequirement
{
    public RussianСitizenshipRequirement(string citizenship)
    {
        Сitizenship = citizenship;
    }

    public string Сitizenship { get; }
}

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

public class RussianСitizenshipHandler : AuthorizationHandler<RussianСitizenshipRequirement>
{
    protected override Task HandleRequirementAsync(AuthorizationHandlerContext context, RussianСitizenshipRequirement requirement)
    {
        if (!context.User.HasClaim(c => c.Type == ClaimTypes.Country))
        {
            return Task.FromResult(0);
        }

        var citizenship = context.User.FindFirst(
            c => c.Type == ClaimTypes.Country).Value;
        
        if (citizenship == requirement.Сitizenship)
        {
            context.Succeed(requirement);
        }
        return Task.CompletedTask;
    }
}

Добавим в HomeController метод RussianPage () c атрибутом Authorize:

[Authorize(Policy = "RussianСitizenship")]
public IActionResult RussianPage()
{
    return View();
}

Готово, доступ к этому методу получат лишь пользователи, удовлетворяющие требованиям данной политики.

Выводы

Это была обзорная статья, из которой видно, что Identity 3.0 является мощным инструментом, , который поддерживает:

  • авторизацию на основе ролей,
  • Claim-Based авторизацию,
  • аутентификацию через соцсети,
  • двухфакторную аутентификацию с подтверждением по смс или по электронной почте и др.

Для большинства сайтов этого достаточно для полноценной работы.

В следующей статье я постараюсь немного кастомизировать Identity и адаптировать его для использования в приложении с многослойной архитектурой.