Implement JWT In .NET Core API

Introduction

 
This article is a step-by-step guide to implementing JWT-based Authentication in ASP.NET Core API.
 
The goal in this article is to first start by learning how JSON Web Tokens (or JWTs) work in detail, including how they can be used for User Authentication, how refresh token, and how to get user detail using JWT token.
 

Way to implement JWT

 
Implement JWT In .NET Core API
  1. Client sends a login request with username and password to server
  2. Server receives the username and password, authenticate the user
  3. If authentication is successful, then the server creates a JWT token called accessToken that stores user public info’s and sends it back to the client.
  4. Client receives the accessToken, from now on, client sends any request to server like get current user, client just attach the accessToken with request.
  5. Server receives a request, authorizes the JWT token, and continues processing the request, and then returns the result to the client.

What is JWT?(JSON Web Token)

 
JSON Web Token (JWT) is an open standard that defines a compact and self-contained way for securely transmitting information between parties as a JSON object. This information can be verified and trusted because it is digitally signed. The tokens are signed either using a private secret or a public/private key pair using RSA or ECDSA.
 

How to Implement JWT Authentication in an ASP.NET Core Web API project.

 
Prerequisites
  • Software
    • Dot NET Core
    • Visual Studio 2017 with last update or Visual Studio 2019
    • SQL Server
  • Skills
    • C# 
Step 1 - Create Project
 
Open Visual Studio Click on “Create a new project”
 
Implement JWT In .NET Core API
 
Select ASP.NET Core Web Application option.

Implement JWT In .NET Core API

Add Project name and Solution name
 
Implement JWT In .NET Core API

Select “API” option with “.NET Core” and “ASP .NET Core 3.1” for create ASP.NET API 

Implement JWT In .NET Core API
Use can see the default folder structure. 

Implement JWT In .NET Core API
 
Step 2 - Install Nuget Packages
 
In this step, we need to install the following NuGet packages:
  1. Microsoft.EntityFrameworkCore.SqlServer
  2. Microsoft.EntityFrameworkCore.Tools
  3. Microsoft.IdentityModel.Tokens
  4. System.IdentityModel.Tokens.Jwt
  5. Microsoft.AspNetCore.Authentication.JwtBearer
Now, we'll proceed to install the above package from Nuget, right-click on TokenDemo.Web project,
 
Implement JWT In .NET Core API

Change to browse tab and type Microsoft.EntityFrameworkCore.SqlServer:
 
Implement JWT In .NET Core API
 
Next,
 
Install Microsoft.EntityFrameworkCore.Tools package
Install Microsoft.IdentityModel.Tokens package
Install System.IdentityModel.Tokens.Jwt package
Install Microsoft.AspNetCore.Authentication.JwtBearer package
 
Step 3 - Create DataContext
 
Here we will follow the database first approach. If you want to use code first approach, you can find database models in the “DataContext” folder in the attached project.
 
Shown below is the relationship between the tables.
Implement JWT In .NET Core API
Now go to the Package Manager Console and fire the command given below with your database server name and database name. 
  1. PM> Scaffold-DbContext "Server=*SERVER_NAME*;Database=*DATABASE_NAME*;Trusted_Connection=True;" Microsoft.EntityFrameworkCore.SqlServer -ContextDir DataContext -Context DemoTokenContext -OutputDir DataContext -Force   
Replace *SERVER_NAME* with your database server name
 
Replace *DATABASE_NAME* with your database name

Implement JWT In .NET Core API

Step 4 - Create Models for the controller
 
Now, create a directory with name Models and add the following files
  • ResponseModel.cs
  • LoginModel.cs
  • AuthenticationResult.cs
  • ServiceConfiguration.cs
ResponseModel.cs will contain definitions for response model.
 
LoginModel.cs will contain definitions for Login Model.
 
AuthenticationResult.cs will contain definitions for Authentication and TokenModel Model.
 
ServiceConfiguration.cs will contain definitions for Authentication and TokenModel Model.
 
Code for AuthenticationResult.cs file,
  1. using Newtonsoft.Json;  
  2. using System.Collections.Generic;  
  3.   
  4. namespace TokenDemo.Web.Models  
  5. {  
  6.     public class TokenModel  
  7.     {  
  8.         [JsonProperty("token")]  
  9.         public string Token { getset; }  
  10.         [JsonProperty("refreshToken")]  
  11.         public string RefreshToken { getset; }  
  12.     }  
  13.   
  14.     public class AuthenticationResult: TokenModel  
  15.     {  
  16.         public bool Success { getset; }  
  17.         public IEnumerable<string> Errors { getset; }  
  18.     }  
  19. }  
Code for ResponseModel.cs file
  1. using Newtonsoft.Json;  
  2.   
  3. namespace TokenDemo.Web.Models  
  4. {  
  5.     public class ResponseModel<T>  
  6.     {  
  7.         public ResponseModel()  
  8.         {  
  9.             IsSuccess = true;  
  10.             Message = "";  
  11.         }  
  12.         [JsonProperty("isSuccess")]  
  13.         public bool IsSuccess { getset; }  
  14.         [JsonProperty("message")]  
  15.         public string Message { getset; }  
  16.         [JsonProperty("data")]  
  17.         public T Data { getset; }  
  18.     }  
  19. }  
Code for LoginModel.cs file
  1. using Newtonsoft.Json;  
  2.   
  3. namespace TokenDemo.Web.Models  
  4. {  
  5.     public class LoginModel  
  6.     {   
  7.         [JsonProperty("userName")]  
  8.         public string UserName { getset; }  
  9.         [JsonProperty("password")]  
  10.         public string Password { getset; }  
  11.     }  
  12. }  
Code for ServiceConfiguration.cs file
  1. using System;  
  2.   
  3. namespace TokenDemo.Web.Models  
  4. {  
  5.     public class ServiceConfiguration  
  6.     {  
  7.         public JwtSettings JwtSettings { getset; }  
  8.     }  
  9.     public class JwtSettings  
  10.     {  
  11.         public string Secret { getset; }  
  12.   
  13.         public TimeSpan TokenLifetime { getset; }  
  14.     }  
  15. }  
Step 5 - Update appsettings.Development.json

Implement JWT In .NET Core API
 
Code for appsettings.Development.json file
  1. {  
  2.   "Logging": {  
  3.     "LogLevel": {  
  4.       "Default""Information",  
  5.       "Microsoft""Warning",  
  6.       "Microsoft.Hosting.Lifetime""Information"  
  7.     }  
  8.   },  
  9.   "ConnectionString": {  
  10.     "DefaultConnection""Data Source=*SERVER_NAME*;Initial Catalog=*DATABASE_NAME*;Persist Security Info=True;User ID=*DATABASE_USERNAME*;Password=*DATABASE_PASSWORD*"  
  11.   },  
  12.   "ServiceConfiguration": {  
  13.     "JwtSettings": {  
  14.       "Secret""*SECRET*",  
  15.       "TokenLifetime""00:00:45"  
  16.     }  
  17.   }  
  18. }  
Replace *SERVER_NAME* with your database server name
Replace *DATABASE_NAME* with your database name
Replace *DATABASE_ USERNAME * with your database user name
Replace *DATABASE_PASSWORD* with your database password
Replace *SECRET* with any string like "DWEYGZH2K4M5N7Q8R9TBUCVEXFYGZJ3K4M6P7Q8SATBUDWEXFZH2J3M5N6"
 
Step 6 - Create Service
 
Now, create a directory with name Services and add the following files
 
Code for IdentityService.cs file
  1. using Microsoft.Extensions.Options;  
  2. using Microsoft.IdentityModel.Tokens;  
  3. using System;  
  4. using System.Collections.Generic;  
  5. using System.IdentityModel.Tokens.Jwt;  
  6. using System.Linq;  
  7. using System.Security.Claims;  
  8. using System.Text;  
  9. using System.Threading.Tasks;  
  10. using TokenDemo.Web.DataContext;  
  11. using TokenDemo.Web.Helpers;  
  12. using TokenDemo.Web.Models;  
  13. using JwtRegisteredClaimNames = System.IdentityModel.Tokens.Jwt.JwtRegisteredClaimNames;  
  14.   
  15. namespace TokenDemo.Web.Services  
  16. {  
  17.     public interface IIdentityService  
  18.     {  
  19.         Task<ResponseModel<TokenModel>> LoginAsync(LoginModel login);  
  20.     }  
  21.   
  22.     public class IdentityService : IIdentityService  
  23.     {  
  24.         private readonly DemoTokenContext _context;  
  25.         private readonly ServiceConfiguration _appSettings;  
  26.   
  27.         private readonly TokenValidationParameters _tokenValidationParameters;  
  28.         public IdentityService(DemoTokenContext context,  
  29.             IOptions<ServiceConfiguration> settings,  
  30.             TokenValidationParameters tokenValidationParameters)  
  31.         {  
  32.             _context = context;  
  33.             _appSettings = settings.Value;  
  34.             _tokenValidationParameters = tokenValidationParameters;  
  35.         }  
  36.   
  37.   
  38.         public async Task<ResponseModel<TokenModel>> LoginAsync(LoginModel login)  
  39.         {  
  40.             ResponseModel<TokenModel> response = new ResponseModel<TokenModel>();  
  41.             try  
  42.             {  
  43.                 string md5Password = MD5Helpers.GenerateMd5Hash(login.Password);  
  44.                 UsersMaster loginUser = _context.UsersMaster.FirstOrDefault(c => c.UserName == login.UserName && c.Password == md5Password);  
  45.   
  46.                 if (loginUser == null)  
  47.                 {  
  48.                     response.IsSuccess = false;  
  49.                     response.Message = "Invalid Username And Password";  
  50.                     return response;  
  51.                 }  
  52.   
  53.                 AuthenticationResult authenticationResult = await AuthenticateAsync(loginUser);  
  54.                 if (authenticationResult != null && authenticationResult.Success)  
  55.                 {  
  56.                     response.Data = new TokenModel() { Token = authenticationResult.Token, RefreshToken = authenticationResult.RefreshToken };  
  57.                 }  
  58.                 else  
  59.                 {  
  60.                     response.Message = "Something went wrong!";  
  61.                     response.IsSuccess = false;  
  62.                 }  
  63.   
  64.                 return response;  
  65.             }  
  66.             catch (Exception ex)  
  67.             {  
  68.                 throw ex;  
  69.             }  
  70.         }  
  71.   
  72.         private List<RolesMaster> GetUserRole(long UserId)  
  73.         {  
  74.             try  
  75.             {  
  76.                 List<RolesMaster> rolesMasters = (from UM in _context.UsersMaster  
  77.                                                   join UR in _context.UserRoles on UM.UserId equals UR.UserId  
  78.                                                   join RM in _context.RolesMaster on UR.RoleId equals RM.RoleId  
  79.                                                   where UM.UserId == UserId  
  80.                                                   select RM).ToList();  
  81.                 return rolesMasters;  
  82.             }  
  83.             catch (Exception)  
  84.             {  
  85.                 return new List<RolesMaster>();  
  86.             }  
  87.         }  
  88.   
  89.         public async Task<AuthenticationResult> AuthenticateAsync(UsersMaster user)  
  90.         {  
  91.             // authentication successful so generate jwt token  
  92.             AuthenticationResult authenticationResult = new AuthenticationResult();  
  93.             var tokenHandler = new JwtSecurityTokenHandler();  
  94.   
  95.             try  
  96.             {  
  97.                 var key = Encoding.ASCII.GetBytes(_appSettings.JwtSettings.Secret);  
  98.   
  99.                 ClaimsIdentity Subject = new ClaimsIdentity(new Claim[]  
  100.                     {  
  101.                     new Claim("UserId", user.UserId.ToString()),  
  102.                     new Claim("FirstName", user.FirstName),  
  103.                     new Claim("LastName",user.LastName),  
  104.                     new Claim("EmailId",user.Email==null?"":user.Email),  
  105.                     new Claim("UserName",user.UserName==null?"":user.UserName),  
  106.                     new Claim(JwtRegisteredClaimNames.Jti, Guid.NewGuid().ToString()),  
  107.                     });  
  108.                 foreach (var item in GetUserRole(user.UserId))  
  109.                 {  
  110.                     Subject.AddClaim(new Claim(ClaimTypes.Role, item.RoleName));  
  111.                 }  
  112.   
  113.                 var tokenDescriptor = new SecurityTokenDescriptor  
  114.                 {  
  115.                     Subject = Subject,  
  116.                     Expires = DateTime.UtcNow.Add(_appSettings.JwtSettings.TokenLifetime),  
  117.                     SigningCredentials = new SigningCredentials(new SymmetricSecurityKey(key), SecurityAlgorithms.HmacSha256Signature)  
  118.                 };  
  119.                 var token = tokenHandler.CreateToken(tokenDescriptor);  
  120.                 authenticationResult.Token = tokenHandler.WriteToken(token);  
  121.                 var refreshToken = new RefreshToken  
  122.                 {  
  123.                     Token = Guid.NewGuid().ToString(),  
  124.                     JwtId = token.Id,  
  125.                     UserId = user.UserId,  
  126.                     CreationDate = DateTime.UtcNow,  
  127.                     ExpiryDate = DateTime.UtcNow.AddMonths(6)  
  128.                 };  
  129.                 await _context.RefreshToken.AddAsync(refreshToken);  
  130.                 await _context.SaveChangesAsync();  
  131.                 authenticationResult.RefreshToken = refreshToken.Token;  
  132.                 authenticationResult.Success = true;  
  133.                 return authenticationResult;  
  134.             }  
  135.             catch (Exception ex)  
  136.             {  
  137.                 return null;  
  138.             }  
  139.   
  140.         }  
  141.     }  
  142. }  
Step 7 - Update Startup.cs
 
Code for Startup.cs file
  1. using Microsoft.AspNetCore.Authentication.JwtBearer;  
  2. using Microsoft.AspNetCore.Builder;  
  3. using Microsoft.AspNetCore.Hosting;  
  4. using Microsoft.EntityFrameworkCore;  
  5. using Microsoft.Extensions.Configuration;  
  6. using Microsoft.Extensions.DependencyInjection;  
  7. using Microsoft.IdentityModel.Tokens;  
  8. using System.Text;  
  9. using TokenDemo.Web.DataContext;  
  10. using TokenDemo.Web.Models;  
  11.   
  12. namespace TokenDemo.Web  
  13. {  
  14.     public class Startup  
  15.     {  
  16.         public Startup(IConfiguration configuration)  
  17.         {  
  18.             Configuration = configuration;  
  19.         }  
  20.   
  21.         public IConfiguration Configuration { get; }  
  22.   
  23.         // This method gets called by the runtime. Use this method to add services to the container.  
  24.         public void ConfigureServices(IServiceCollection services)  
  25.         {  
  26.             //services.AddControllers();  
  27.             services.AddMvc();  
  28.             services.AddDbContext<DemoTokenContext>(opts => opts.UseSqlServer(Configuration["ConnectionString:DefaultConnection"]));  
  29.             // configure strongly typed settings objects  
  30.             var appSettingsSection = Configuration.GetSection("ServiceConfiguration");  
  31.             services.Configure<ServiceConfiguration>(appSettingsSection);  
  32.             services.AddTransient<Services.IIdentityService, Services.IdentityService>();  
  33.             // configure jwt authentication  
  34.             var serviceConfiguration = appSettingsSection.Get<ServiceConfiguration>();  
  35.             var JwtSecretkey = Encoding.ASCII.GetBytes(serviceConfiguration.JwtSettings.Secret);  
  36.             var tokenValidationParameters = new TokenValidationParameters  
  37.             {  
  38.                 ValidateIssuerSigningKey = true,  
  39.                 IssuerSigningKey = new SymmetricSecurityKey(JwtSecretkey),  
  40.                 ValidateIssuer = false,  
  41.                 ValidateAudience = false,  
  42.                 RequireExpirationTime = false,  
  43.                 ValidateLifetime = true  
  44.             };  
  45.             services.AddSingleton(tokenValidationParameters);  
  46.             services.AddAuthentication(x =>  
  47.             {  
  48.                 x.DefaultAuthenticateScheme = JwtBearerDefaults.AuthenticationScheme;  
  49.                 x.DefaultScheme = JwtBearerDefaults.AuthenticationScheme;  
  50.                 x.DefaultChallengeScheme = JwtBearerDefaults.AuthenticationScheme;  
  51.   
  52.             })  
  53.             .AddJwtBearer(x =>  
  54.             {  
  55.                 x.RequireHttpsMetadata = false;  
  56.                 x.SaveToken = true;  
  57.                 x.TokenValidationParameters = tokenValidationParameters;  
  58.   
  59.             });  
  60.             services.AddCors(options =>  
  61.             {  
  62.                 options.AddPolicy("CorsPolicy", builder =>  
  63.                 builder.AllowAnyOrigin()  
  64.              .AllowAnyMethod()  
  65.              .AllowAnyHeader()  
  66.              );  
  67.             });  
  68.         }  
  69.   
  70.         // This method gets called by the runtime. Use this method to configure the HTTP request pipeline.  
  71.         public void Configure(IApplicationBuilder app, IWebHostEnvironment env)  
  72.         {  
  73.             app.UseHttpsRedirection();  
  74.             app.UseRouting();  
  75.             app.UseCors("CorsPolicy");  
  76.             app.UseAuthentication();  
  77.             app.UseAuthorization();  
  78.             app.UseStaticFiles();  
  79.             app.UseEndpoints(endpoints =>  
  80.             {  
  81.                 endpoints.MapControllers();  
  82.             });  
  83.         }  
  84.     }  
  85. }  
Step 8 - Add Controller
 
Now, add the AuthController.cs files in Controller’s folder
 
Code for AuthController.cs file
  1. using Microsoft.AspNetCore.Mvc;  
  2. using System.Threading.Tasks;  
  3. using TokenDemo.Web.Models;  
  4. using TokenDemo.Web.Services;  
  5.   
  6. namespace TokenDemo.Web.Controllers  
  7. {  
  8.     [Route("api/[controller]")]  
  9.   
  10.     [ApiController]  
  11.     public class AuthController : ControllerBase  
  12.     {  
  13.         private readonly IIdentityService _identityService;  
  14.         public AuthController(IIdentityService identityService)  
  15.         {  
  16.             _identityService = identityService;  
  17.         }  
  18.         [Route("login")]  
  19.         [HttpPost]  
  20.         public async Task<IActionResult> LoginAsync([FromBody]LoginModel loginModel)  
  21.         {  
  22.             var result = await _identityService.LoginAsync(loginModel);  
  23.             return Ok(result);  
  24.         }  
  25.     }  
  26. }  
Step 9 - Running Web API
 
Now, press F5 to start debugging the Web API project, if everything is OK, we'll get the following output in the browser
 
Implement JWT In .NET Core API
Now, we will call the login API and get the Access Token and Refresh Token. For calling login API, we have to use Postman.
 
As per the below screenshot, we will call Login API and get the Access Token and Refresh.
 
Implement JWT In .NET Core API
 
Now we decode our Access Token on the site “https://jwt.io/”. As per below screenshot you can see the Decoded user information which we added for Encoded “AuthenticateAsync” in IdentityService service.
 
Implement JWT In .NET Core API
 
Now we have to implement Refresh Token functionality, the below diagram shows a way to implement the refresh token functionality.
 
Implement JWT In .NET Core API

Step 10 - Update IdentityService
 
Now, following is the code for refresh token, so append the below code in IdentityService.cs
  1. public async Task<ResponseModel<TokenModel>> RefreshTokenAsync(TokenModel request)  
  2. {  
  3.     ResponseModel<TokenModel> response = new ResponseModel<TokenModel>();  
  4.     try  
  5.     {  
  6.         var authResponse = await GetRefreshTokenAsync(request.Token, request.RefreshToken);  
  7.         if (!authResponse.Success)  
  8.         {  
  9.       
  10.             response.IsSuccess = false;  
  11.             response.Message = string.Join(",", authResponse.Errors);  
  12.             return response;  
  13.         }  
  14.         TokenModel refreshTokenModel = new TokenModel();  
  15.         refreshTokenModel.Token = authResponse.Token;  
  16.         refreshTokenModel.RefreshToken = authResponse.RefreshToken;  
  17.         response.Data = refreshTokenModel;  
  18.         return response;  
  19.     }  
  20.     catch (Exception ex)  
  21.     {  
  22.          
  23.       
  24.         response.IsSuccess = false;  
  25.         response.Message = "Something went wrong!";  
  26.         return response;  
  27.     }  
  28. }  
  29.   
  30. private async Task<AuthenticationResult> GetRefreshTokenAsync(string token, string refreshToken)  
  31. {  
  32.     var validatedToken = GetPrincipalFromToken(token);  
  33.   
  34.     if (validatedToken == null)  
  35.     {  
  36.         return new AuthenticationResult { Errors = new[] { "Invalid Token" } };  
  37.     }  
  38.   
  39.     var expiryDateUnix =  
  40.         long.Parse(validatedToken.Claims.Single(x => x.Type == JwtRegisteredClaimNames.Exp).Value);  
  41.   
  42.     var expiryDateTimeUtc = new DateTime(1970, 1, 1, 0, 0, 0, DateTimeKind.Utc)  
  43.         .AddSeconds(expiryDateUnix);  
  44.   
  45.     if (expiryDateTimeUtc > DateTime.UtcNow)  
  46.     {  
  47.         return new AuthenticationResult { Errors = new[] { "This token hasn't expired yet" } };  
  48.     }  
  49.   
  50.     var jti = validatedToken.Claims.Single(x => x.Type == JwtRegisteredClaimNames.Jti).Value;  
  51.   
  52.     var storedRefreshToken = _context.RefreshToken.FirstOrDefault(x => x.Token == refreshToken);  
  53.   
  54.     if (storedRefreshToken == null)  
  55.     {  
  56.         return new AuthenticationResult { Errors = new[] { "This refresh token does not exist" } };  
  57.     }  
  58.   
  59.     if (DateTime.UtcNow > storedRefreshToken.ExpiryDate)  
  60.     {  
  61.         return new AuthenticationResult { Errors = new[] { "This refresh token has expired" } };  
  62.     }  
  63.   
  64.     if (storedRefreshToken.Used.HasValue && storedRefreshToken.Used == true)  
  65.     {  
  66.         return new AuthenticationResult { Errors = new[] { "This refresh token has been used" } };  
  67.     }  
  68.   
  69.     if (storedRefreshToken.JwtId != jti)  
  70.     {  
  71.         return new AuthenticationResult { Errors = new[] { "This refresh token does not match this JWT" } };  
  72.     }  
  73.   
  74.     storedRefreshToken.Used = true;  
  75.     _context.RefreshToken.Update(storedRefreshToken);  
  76.     await _context.SaveChangesAsync();  
  77.     string strUserId = validatedToken.Claims.Single(x => x.Type == "UserId").Value;  
  78.     long userId = 0;  
  79.     long.TryParse(strUserId, out userId);  
  80.     var user = _context.UsersMaster.FirstOrDefault(c => c.UserId == userId);  
  81.     if (user == null)  
  82.     {  
  83.         return new AuthenticationResult { Errors = new[] { "User Not Found" } };  
  84.     }  
  85.       
  86.     return await AuthenticateAsync(user);  
  87. }  
  88.   
  89. private ClaimsPrincipal GetPrincipalFromToken(string token)  
  90. {  
  91.     var tokenHandler = new JwtSecurityTokenHandler();  
  92.   
  93.     try  
  94.     {  
  95.         var tokenValidationParameters = _tokenValidationParameters.Clone();  
  96.         tokenValidationParameters.ValidateLifetime = false;  
  97.         var principal = tokenHandler.ValidateToken(token, tokenValidationParameters, out var validatedToken);  
  98.         if (!IsJwtWithValidSecurityAlgorithm(validatedToken))  
  99.         {  
  100.             return null;  
  101.         }  
  102.   
  103.         return principal;  
  104.     }  
  105.     catch  
  106.     {  
  107.         return null;  
  108.     }  
  109. }  
  110.   
  111. private bool IsJwtWithValidSecurityAlgorithm(SecurityToken validatedToken)  
  112. {  
  113.     return (validatedToken is JwtSecurityToken jwtSecurityToken) &&  
  114.            jwtSecurityToken.Header.Alg.Equals(SecurityAlgorithms.HmacSha256,  
  115.                StringComparison.InvariantCultureIgnoreCase);  
  116. }  
Update IIdentityService interface
  1. public interface IIdentityService  
  2. {  
  3.     Task<ResponseModel<TokenModel>> LoginAsync(LoginModel login);  
  4.     Task<ResponseModel<TokenModel>> RefreshTokenAsync(TokenModel request);  
  5. }  
Step 11 - Update AuthController
  1. [Route("refresh")]  
  2. [HttpPost]  
  3. public async Task<IActionResult> Refresh([FromBody] TokenModel request)  
  4. {  
  5.     var result = await _identityService.RefreshTokenAsync(request);  
  6.     return Ok(result);  
  7. }  
Step 12 - Running Web API
 
Again we will call login API endpoint and copy Access Token and Refresh Token or if you have old Access Token and Refresh copy that which we get in last call.
 
As per below screenshot we called Login API endpoint and copy Access Token and Refresh Token for call Refresh Token API endpoint.
 
Implement JWT In .NET Core API
 
As per the below screenshot, we called the Refresh Token API endpoint and regenerated the Access Token and Refresh Token.

Implement JWT In .NET Core API
 
Now we got user information using Access Token
 
Step 13 - Add UserService
 
Now, add the UserService.cs files in Services folder
 
Code for UserService.cs file
  1. using System;  
  2. using System.Collections.Generic;  
  3. using System.Linq;  
  4. using TokenDemo.Web.DataContext;  
  5. using TokenDemo.Web.Models;  
  6.   
  7. namespace TokenDemo.Web.Services  
  8. {  
  9.     public interface IUserService  
  10.     {  
  11.         ResponseModel<UserModel> Get(long UserId);  
  12.     }  
  13.     public class UserService: IUserService  
  14.     {  
  15.         private readonly DemoTokenContext _context;  
  16.           
  17.         public UserService(DemoTokenContext context)  
  18.         {  
  19.             _context = context;  
  20.         }  
  21.         public ResponseModel<UserModel> Get(long UserId)  
  22.         {  
  23.             ResponseModel<UserModel> response = new ResponseModel<UserModel>();  
  24.   
  25.             try  
  26.             {  
  27.                 UserModel user = (from UM in _context.UsersMaster  
  28.                                                   where UM.UserId == UserId  
  29.                                                   select new UserModel {  
  30.                                                   UserId=UM.UserId,  
  31.                                                   FirstName=UM.FirstName,  
  32.                                                   LastName=UM.LastName,  
  33.                                                   Email=UM.Email,  
  34.                                                   PhoneNumber=UM.PhoneNumber,  
  35.                                                   UserName=UM.UserName  
  36.                                                   } ).FirstOrDefault();  
  37.                 List<string> roleNames = (from UM in _context.UsersMaster  
  38.                                                   join UR in _context.UserRoles on UM.UserId equals UR.UserId  
  39.                                                   join RM in _context.RolesMaster on UR.RoleId equals RM.RoleId  
  40.                                                   where UM.UserId == UserId  
  41.                                                   select RM.RoleName).ToList();  
  42.                 if (user != null)  
  43.                 {  
  44.                     user.UserRoles = roleNames;  
  45.                     response.Data = user;  
  46.                     return response;  
  47.                 }  
  48.                 else  
  49.                 {  
  50.                     response.IsSuccess = false;  
  51.                     response.Message = "User Not Found!";  
  52.                     return response;  
  53.                 }  
  54.             }  
  55.             catch (Exception ex)  
  56.             {  
  57.   
  58.                 throw ex;  
  59.             }  
  60.         }  
  61.     }  
  62. }   
Step 14 - Add UsersController
 
Now, add the UsersController.cs files in Controllers folder.
 
Code for UsersController.cs file
  1. using Microsoft.AspNetCore.Authorization;  
  2. using Microsoft.AspNetCore.Http;  
  3. using Microsoft.AspNetCore.Mvc;  
  4. using System.Collections.Generic;  
  5. using System.Security.Claims;  
  6. using TokenDemo.Web.Services;  
  7.   
  8. namespace TokenDemo.Web.Controllers  
  9. {  
  10.     [Route("api/[controller]")]  
  11.     [ApiController]  
  12.     public class UsersController : ControllerBase  
  13.     {  
  14.         private readonly IUserService _userService;  
  15.         public UsersController(IUserService userService)  
  16.         {  
  17.             _userService = userService;  
  18.         }  
  19.   
  20.         [Route("getCurrentUser")]  
  21.         [HttpGet]  
  22.         [Authorize]  
  23.         public IActionResult GetCurrentUser()  
  24.         {  
  25.             long UserId = GetUserIdFromToken();  
  26.             var result = _userService.Get(UserId);  
  27.             return Ok(result);  
  28.         }  
  29.   
  30.         protected long GetUserIdFromToken()  
  31.         {  
  32.             long UserId = 0;  
  33.             try  
  34.             {  
  35.                 if (HttpContext.User.Identity.IsAuthenticated)  
  36.                 {  
  37.                     var identity = HttpContext.User.Identity as ClaimsIdentity;  
  38.                     if (identity != null)  
  39.                     {  
  40.                         IEnumerable<Claim> claims = identity.Claims;  
  41.                         string strUserId = identity.FindFirst("UserId").Value;  
  42.                         long.TryParse(strUserId, out UserId);  
  43.   
  44.                     }  
  45.                 }  
  46.                 return UserId;  
  47.             }  
  48.             catch  
  49.             {  
  50.                 return UserId;  
  51.             }  
  52.         }  
  53.     }  
  54. }  
Step 15 - Update Startup.cs
 
Append the below code in Startup.cs file ConfigureServices method
  1. services.AddTransient<Services.IUserService, Services.UserService>();  
Step 16 - Run Application
 
Run your application and get user information using Authorize.
 
In the below screenshot we are getting user information using Access Token which we get in the call to login to the API endpoint.
 
Implement JWT In .NET Core API