Quote of the Day

more Quotes

Categories

Get notified of new posts

Buy me coffee

Configure OAuth2 implicit flow for Swagger UI

In this post, I share some example codes of how to enable OAuth2 implicit flow within Swagger UI to obtain an access token from Microsoft Identity Framework (v2.0 endpoint).

In case you are not familiar with Swagger, it is also known as Open API, and is a tool for generating documentation for web APIs. A Swagger document is a JSON that conforms to the Open API Spec. The document can further be fed into other tool such as Swagger UI, which is a client, web-based UI that displays the document and provides interactive tools to generate and send requests based on the JSON document.

Register applications in Azure AD

You want to register two applications, one for the API which acts as a resource server, and one for Swagger UI which acts as a client application in the OAuth2 implicit flow.

For instructions on registering an application in Azure AD, checkout the documentation.

Register ASP.NET core web API

When registering the API, you also need to define the scopes via “Expose an API”. For a v2.0 endpoint, a scope path is a full URI which by default begins with api://{AppIdentifier} where AppIdentifier is the client id of the registered app. You can also authorize another application for the scopes in advance such that the users do not need to consent when the application requests access to the API.

Define scopes for API app in Azure AD.

Register Swagger UI

Swagger UI needs to authenticate with Azure AD to obtain an access token for calling the API. When registering an application for Swagger, you also need to generate a secret or upload a certificate. When requesting an access token, Swagger UI uses the client id and secret/certificate to authenticate against Azure AD. You can generate the secret or upload a certificate under Certificates & secrets.

Generate a secret for using as the app’s password when authenticating against Azure AD to obtain an access token

If you use Swagger UI in the browser, one of the suitable OAuth2 flow you can use is the implicit flow. Upon successful authentication of an implicit flow, Azure AD sends back the access token to the reply URL that you configure when registering the application. For Swagger UI, the reply URL may end in “oauth2-redirect.html” as shown in the screenshot below.

Set reply url to which Azure AD sends an access token.

Add the nuget package

Add the packages below to your ASP.NET core .csproj file to use Swagger:

<PackageReference Include="Microsoft.OpenApi" Version="1.1.4" />
<PackageReference Include="Swashbuckle.AspNetCore" Version="5.0.0-rc2" />

Add services for Swagger to the service container

The below snippets configure Swagger UI to support obtaining an access token via implicit flow.

// Extension method for registering Swagger with the service container.  
public static IServiceCollection AddSwagger(this IServiceCollection services, ServicePrinciples servicePrinciples)
        {
            services.AddSwaggerGen(c =>
            {
                .... // other configurations omitted for brevity 
 
                c.AddSecurityDefinition("oauth2", new OpenApiSecurityScheme()
                {
                    Type = SecuritySchemeType.OAuth2,
                    Flows = new OpenApiOAuthFlows()
                    {
                        Implicit = new OpenApiOAuthFlow()
                        {
                            TokenUrl = new Uri($"{servicePrinciples.Api.Instance}/{servicePrinciples.Api.TenantId}/oauth2/v2.0/token"),
                            AuthorizationUrl = new Uri($"{servicePrinciples.Api.Instance}/{servicePrinciples.Api.TenantId}/oauth2/v2.0/authorize"),
                            Scopes = { { servicePrinciples.Api.Scope, servicePrinciples.Api.ScopeDescription } }
                        }
                    }
                }) ;
            });
            return services; 
        }

Below show the variables in appsettings.

/// service principal registered in azure for verifying access tokens.
  "AADGov": {
    "Api": {
      "ClientId": "********-****-****-****-123456789076",
      "TenantId": "********-****-****-****-12345678907e",
      "Instance": "https://login.microsoftonline.com",
      "Scope": "api://********-****-****-****-123456789076/full",
      "ScopeDescription":  "Full access"
    },
    "SwaggerClient": {
      "ClientId": "********-****-****-****-123456789e4",
      "TenantId": "********-****-****-****-12345678907e"
    }
  }

Use SwaggerUI

The codes below pre populates the client id and secret for when the user clicks on the Authorize button in Swagger UI.

// This method gets called by the runtime. Use this method to configure the HTTP request pipeline.
       public void Configure(IApplicationBuilder app, IHostingEnvironment env)
       {
              
           // Enable middleware to serve swagger-ui (HTML, JS, CSS, etc.), 
           // specifying the Swagger JSON endpoint. 
           app.UseSwaggerUI(c =>
           {
               c.SwaggerEndpoint("/swagger/v1/swagger.json", "Your API");
               c.RoutePrefix = string.Empty;
               c.OAuthClientId(_servicePrinciples.SwaggerClient.ClientId);
               c.OAuthScopeSeparator(" ");
           });
           ...
       }
   }

If everything is correct, you will see the Authorize button in Swagger UI. Upon clicking on the button, Swagger UI shows the configured flow to obtain authorization.

Configure OAuth2 implicit flow for Swagger UI

SwashBuckle supports other flows such as Client-Credentials, resource owner credentials, and authorization flow. If you use the client credentials flow, keep in mind you may run into issues because of CORS policy. When I attempted the client credentials flow, I could not obtain an access token because the browser did not allow the connection from my local machine to Microsoft.

References

https://docs.microsoft.com/en-us/graph/auth-register-app-v2

https://swagger.io/

https://docs.microsoft.com/en-us/aspnet/core/tutorials/web-api-help-pages-using-swagger?view=aspnetcore-3.0

1 comment