Skip to content

IdentityServer4

Denys Liienko edited this page Jul 27, 2022 · 5 revisions

1. What is IdentityServer4?

IdentityServer4 is an OpenID Connect and OAuth 2.0 framework for ASP.NET Core. It provides infrastructure(tables in database) that deal with users' identity, roles, authentication, etc. (UserIdentity, Roles, Scopes).

2. What are OAuth and OpenID Connect?

OAuth 2.0 which stands for “Open Authorization”, is a standard designed to allow a website or application to access resources hosted by other web apps on behalf of a user. OAuth 2.0 provides consented access and restricts actions of what the client app can perform on resources on behalf of the user, without ever sharing the user's credentials.

OpenID Connect 1.0 is a simple identity layer on top of the OAuth 2.0 protocol. It allows Clients to verify the identity of the End-User based on the authentication performed by an Authorization Server, as well as to obtain basic profile information about the End-User in an interoperable and REST-like manner.

Authentication - verifies who the user is.

Authorization determines what resources a user can access.

                        OAuth protocol flow

 +--------+                               +---------------+
 |        |--(A)- Authorization Request ->|   Resource    |
 |        |                               |     Owner     |
 |        |<-(B)-- Authorization Grant ---|               |
 |        |                               +---------------+
 |        |
 |        |                               +---------------+
 |        |--(C)-- Authorization Grant -->| Authorization |
 | Client |                               |     Server    |
 |        |<-(D)----- Access Token -------|               |
 |        |                               +---------------+
 |        |                                    ↑     |
 |        |                 Token verification |     | Token verification
 |        |                      request       |     |      response
 |        |                                    |     ↓
 |        |                               +---------------+
 |        |--(E)----- Access Token ------>|    Resource   |
 |        |                               |     Server    |
 |        |<-(F)--- Protected Resource ---|               |
 +--------+                               +---------------+

3. Basic setup

There are two fundamental ways to start a new IdentityServer project:

  • start from scratch
  • start with the ASP.NET Identity template in Visual Studio In this project the project is built from scratch. Create a new ASP.NET Core project image
    Select "Empty" WEB app option Install the IdentityServer4 nuget package image
    Alternatively you can use Package Manager Console: Install-Package IdentityServer4
    or .NET CLI: dotnet add package IdentityServer4

4. Project structure with IdentityServer4

Before we dive into IdentityServer4 configuration, let's examine the project's structure. Authorization server we are going to build with the IdentityServer4 framework is just an ASP.NET Core application with installed IdentityServer4 nuget-package, and authorization flow, data store(operational, configurational), clients, and resources configured. image

  • Migrations- EntityFramework Core migrations for database where operational and configurational data is stored. In our case, only operational data is persisted in db, configurational one is in-memory.
  • ServicesInstaller- static class with extension methods that add necessary services to DI container
  • ProfileService- implements IProfileService interface exported from IdentityServer4 library. Determines what data about a user is displayed in tokens and whether a user is active(not banned or deleted in our application).
  • Config- static class with IdentityServer configurations

5. IdentityServer4 configuration

5.1 Clients, Api/Identity Resources, Scopes

In order to understand what clients, resources, and scopes should be authorized, IdentityServer is configured with the following data:

  • IdentityResources - info about users that can be retrieved in access tokens as claims.
  • ApiResources - WEB APIs protected by IdentityServer
  • ApiScopes - subsets of available endpoints in API. In this project protected vet clinic API is one entire scope
  • Clients - apps that consume WEB APIs. In the project, there are 2 configured clients: the Postman client(for development and WEB API testing in Postman) and the Angular client.

Clients, APIs, etc. configurations are in Config.cs Configuration applied while adding IdnetityServer to DI container: image

5.2 Operational store (SQL Server)

In order to store persisted grants(refresh tokens) somewhere in a database. We need to provide a connection string to the target DB. In this project, EntityFramework is used as DB provider. So we need to install IdentityServer4.EntityFramework package:

Package-Manager: Install-Package IdentityServer4.EntityFramework
.NET CLI: dotnet add package IdentityServer4.EntityFramework

Configuration applied while adding IdnetityServer to DI container: image

5.3 Migrations to DB

To add a table to DB that stores refresh tokens we have to create and apply EF Migrations in IdentityServer4 project. Enter the following command in IdentityServer project directory:

  • Package-Manager: UpdateDatabase -Context PersistedGrantDbContext
  • EF Core CLI: dotnet-ef database update —context PersistedGrantDbContext

5.4 ProfileService

This service is needed if you want to send additional claims in access tokens(like role) or/and implement a display of info whether the user is active/inactive(is deleted): ProfileService.cs

6. Secure WEB API with IdentityServer4

To secure WEB API we have to add authentication configuration to DI container. In options we have to configure:

  • Authority - URL of IdentityServer
  • Audience - WEB API protected by IS
  • TokenValidationParameters - validation settings. Token expiry have to be checked here

Web API Host configuration

After that you can decorate controllers or separate methods with [Authorize] attributes: image

7. Request and use of tokens

7.1 How to request tokens via HTTP:

  • With user credentials:
    image
    Where offline_access scope stands for receiving a refresh token
  • With refresh token:
    image

7.2 Use access tokens in HTTP requests to WEB API

image

7.3 Interceptors on client(Angular)

Since we are using the same grant type (password) on the client, so the mechanism of token requests and usage is similar to that described above, unless it is automated with TypeScript.

Here you can explore how tokens are requested during login: auth.service.ts

And here how tokens are injected into http requests: auth.interceptor.ts