IdentityServer4 combat - AccessToken life cycle analysis

I. Introduction

This series of IdentityServer4 combat mainly introduces some of the problems that are easy to occur in the actual use process in IdentityServer4 (hereinafter referred to as ids4), as well as the use skills, which are updated from time to time. Thank you for your attention. Friends who have used ids4 should know that AccessTokenLifetimethe survival time of AccessToken can be controlled by setting properties, but careful friends may find that the Token can still be authorized after it expires. Uncover the mystery.

2. About ID Token and AccessToken

Openid Connect (hereinafter referred to as: OIDC) is extended on the OAuth2.0 protocol, IODC=Identity+OAuth2.0, so that it has the function of identity authentication + authorization. It builds an identity layer on top of OAuth2, which is an identity authentication standard protocol based on the OAuth2 protocol. We all know that OAuth2 is an authorization protocol, and it cannot provide complete authentication functions. OIDC uses the OAuth2 authorization server to provide user authentication for third-party clients, and transmits the corresponding authentication information to the client. It is suitable for various types of clients (such as server applications, mobile APPs, JS applications), and is fully compatible with OAuth2, which means that after you build an OIDC service, it can also be used as an OAuth2 service. The application scenario is shown in the figure:

OAuth2 provides Access Token to solve the problem of authorizing third-party clients to access protected resources; OIDC provides ID Token on this basis to solve the problem of third-party client identification and user authentication. The core of OIDC is that in the OAuth2 authorization process, the user's identity authentication information (ID Token) is provided to the third-party client. The ID Token is packaged in JWT format, thanks to the self-contained nature of JWT (JSON Web Token). The security, compactness, and tamper-proof mechanism make ID Token safe to pass to third-party client programs and be easily verified. In addition, the interface of UserInfo is provided, and the user can obtain more complete information of the user.

In a nutshell, ID Token is data in JWT format, which contains the authentication information of a human user. An example of an ID Token is as follows:

{
     "iss": "https://server.example.com",
     "sub": "24400320",
     "aud": "s6BhdRkqt3",
    "nonce": "n-0S6_WzA2Mj",
     "exp": 1311281970,
    "iat": 1311280970,
     "auth_time": 1311280969,
     "acr": "urn:mace:incommon:iap:silver"
 }

Does the above data feel familiar? This is an "AccessToken" we applied for from ids4:

eyJhbGciOiJSUzI1NiIsImtpZCI6IjhlM2U2MWY1ZWUyZDgwMGNlYjE2NmE5NGRjODczMTY0IiwidHlwIjoiSldUIn0.eyJuYmYiOjE1MjU1Nzg3MTUsImV4cCI6MTUyNTU3ODcxNiwiaXNzIjoiaHR0cDovL2xvY2FsaG9zdDo1MDAwIiwiYXVkIjpbImh0dHA6Ly9sb2NhbGhvc3Q6NTAwMC9yZXNvdXJjZXMiLCJhcGkxIl0sImNsaWVudF9pZCI6InJvLmNsaWVudCIsInN1YiI6IjEiLCJhdXRoX3RpbWUiOjE1MjU1Nzg3MTUsImlkcCI6ImxvY2FsIiwic2NvcGUiOlsiYXBpMSJdLCJhbXIiOlsicHdkIl19.JXU4bXUqf8QD4zQz61XC2WTKURtNIVhH23zQPJzOmEtYbQvO2oRP58sCfDQxADeImZ7O0vH4YXIfL8j60B-sAYJev7c2hnjVhHTJ0t-0bUPlLs43cqNG6RarZ8FyfHyhrvIwYBpJXKNROfr6GfLb4Vdpw4ZEd4AC2k2tHuKMfyrrTzqS0oUs1RwqH7KZ1W7pXDr_V2L4PjgCqOQelXAB_V5YXzR9E52FIXnKNzCVnWHmhiTSWg-ptONOoHss1a-ElWejXskTlMBQitnxSno05s4O6vp5R8zqMuo3j57SnPZVaTuR4AUVpDdVmFF9x9k-fHuXyqarsW6YGsXgTTA2Lw

We can see that by decoding the Token above:

I think you can see where our ID Token is without me having to say more.

3. Set the AccessToken expiration time

When we set our client resources on the ids side, there is an AccessTokenLifetimeattribute. This attribute can set the valid time of the Token we apply for, in seconds. The default is 3600 seconds, which is one hour.

Code example:

new Client
{
    ClientId = "ro.client",
    AllowedGrantTypes = GrantTypes.ResourceOwnerPassword,
    AccessTokenLifetime = 5,
    ClientSecrets = 
    {
        new Secret("secret".Sha256())
    },
    AllowedScopes = { "api1" }
}

The code used in this article is the second QuickStart in the ids4 document, and the address will be given at the end of the article.

The Client object also contains an IdentityTokenLifetimeattribute, which is used to set the survival time of the ID Token. However, after we obtain the AccessToken, we use authorization to access API resources, etc. This attribute cannot affect the validity period of the AccessToken, which is also the ID I explained above. The reason for the difference between Token and AccessToken, I hope you don't get confused.

We set the survival time of AccessToken to 5s above. Let's modify the code of the client and let him pause for 6s to access the APi resources again to see what happens:

Let's first look at the returned AccessToken information, the expiration time has become 5s:

Take a look at the results after the pause:

It can be seen that the Token should have expired and cannot be accessed, but the information was successfully obtained by accessing the API:

What's going on here, it's a little different from what we thought, please listen to the next section!

4. Time offset (ClockSkew)

There is such a scenario, if your AccessToken expires in 5s, then you use this AccessToken to access API resources, but the network is blocked at this time, and the request may take 10s to reach the target, then what should I do? If you need to keep the AccessToken you hold always valid, do you need to refresh it in advance or apply for the AccessToken again? If the time difference between your local time and the time of the API resource service may be a few seconds, tens of seconds, etc., how do you judge Validity of the AccessToken you hold?

All of the above problems are due to our idealization of time, so when our API resources are requested to be verified according to AccessToken, there will be a time offset. In layman's terms, the logical expiration time of AccessToken is delayed. , the default time is 5 minutes . For example, our AccessToken should be 2018年5月6日16:50:55expired. In fact, when the API resource is verified, the AccessToken is still valid within five minutes after the expiration time, that is, when the API resource is verified, the real expiration time of the AccessToken is 2018年5月6日16:55:55, this time difference is used to solve the above problem. This is why we set the AccessToken to expire in 5s above, but in fact, it can be used to successfully access the API after 5s.

This setting is for JWT and needs attention here.

5. Set the time offset

1. Get the default expiration time

The default expiration time can be obtained through the properties of the JwtBearerOptionsobject's TokenValidationParametersproperties ClockSkew.

You can see that the default time offset is 5 minutes, so how to customize this value.

2. Set the time offset

We can customize the time offset through the properties IdentityServerAuthenticationOptionsprovided by the object . This setting is in the API resource , because when we request the API resource, the API resource verifies by itself.JwtValidationClockSkew

code show as below:

public void ConfigureServices(IServiceCollection services)
{
    services.AddMvcCore()
        .AddAuthorization()
        .AddJsonFormatters();
    services.AddAuthentication("Bearer")
        .AddIdentityServerAuthentication(options =>
        {
            options.Authority = "http://localhost:5000";
            options.RequireHttpsMetadata = false;
            options.JwtValidationClockSkew = TimeSpan.FromSeconds(0);
            options.ApiName = "api1";
        });
}

By options.JwtValidationClockSkew = TimeSpan.FromSeconds(0);setting this time offset to 0s, then we now run our previous program, set the AccessToken expiration time to 5s, and we pause for 6s, what will happen.

You can see the prompt "Unauthorized", and you can see that the current situation is consistent with what we thought before. That's what time offset does.

6. Write at the end

In the actual production environment, it is necessary to keep the time synchronization of each service and each node as much as possible, and use the standard time. Then this time offset is not recommended to change if there are no special requirements. This is how it is designed, and the official does not recommend changing it. If the setting is too short, it may cause the problems mentioned in the article. Welcome everyone to join the QQ group (4656606) to communicate with me. Many friends in the group have asked this question before writing this article.

Download the code used in this article:

https://github.com/stulzq/BlogDemos/tree/master/ids4AccessTokenLifetime

References:

Guess you like

Origin http://43.154.161.224:23101/article/api/json?id=325618992&siteId=291194637