I use JWT tokens in my ASP.NET Core 2 web application
If the JWT token fails I still want the controller method to be hit but the ASP.NET Identity User object will just be null. Currently the controller method won't get entered if authentication fails so I can't apply logic inside the method to deal with non authenticated users which I want to deal with as guests instead of blocking them.
My code:
Startup.cs
public void ConfigureServices(IServiceCollection services)
{
services.AddAuthentication()
.AddJwtBearer(cfg =>
{
cfg.TokenValidationParameters = new TokenValidationParameters()
{
ValidIssuer = _config["Tokens:Issuer"],
ValidAudience = _config["Tokens:Audience"],
IssuerSigningKey = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(_config["Tokens:Key"]))
};
});
When a user logs in
private IActionResult CreateToken(ApplicationUser user, IList<string> roles)
{
var claims = new List<Claim>
{
new Claim(JwtRegisteredClaimNames.Sub, user.Id.ToString()),
new Claim(JwtRegisteredClaimNames.Jti, Guid.NewGuid().ToString()),
new Claim(JwtRegisteredClaimNames.UniqueName, user.UserName)
};
var key = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(_config["Tokens:Key"]));
var creds = new SigningCredentials(key, SecurityAlgorithms.HmacSha256);
var token = new JwtSecurityToken(
_config["Tokens:Issuer"],
_config["Tokens:Audience"],
claims.ToArray(),
expires: DateTime.Now.AddMinutes(60),
signingCredentials: creds);
var results = new
{
token = new JwtSecurityTokenHandler().WriteToken(token),
expiration = token.ValidTo,
};
return Created("", results);
I make sure after authenticated the various API calls pass the JWT token.
In my Controller I make use of an Authorize attribute
[Authorize(AuthenticationSchemes = JwtBearerDefaults.AuthenticationScheme)]
public class MyController : Controller
{
This allows me to capture the logged in user with the following code for the various API calls
var loggedInUser = User.Identity.Name;
If I remove the authorize attribute then User.Identity.Name will always be null even if the user is authenticated.
How do I use the authorize attribute but still allow the controller method to be entered if the token is not valid? I want to use the same method for both Authorized and non Authorized users to be entered. I will then use the User.Identity.Name to determine if they are not authenticated and have guest user logic inside the method for them.
AuthorizeWithGuestsand put the logic inside of that attribute where you will do your checks and see if the user is not authenticated than treat that users as a guest. - Edward Chopuryan[AuthorizeWithGuests]- Edward Chopuryan