.Net Core : Token based Authentication in webAPI

.Net Core : Token based Authentication in webAPI



Startup.cs


public void ConfigureServices(IServiceCollection services)
        {
            services.AddDbContextPool<AppDbContext>(options => options.UseSqlServer(Configuration.GetConnectionString("DotNetCoreDB")));

            services.AddIdentity<IdentityUser, IdentityRole>()
                    .AddEntityFrameworkStores<AppDbContext>()
                    .AddDefaultTokenProviders();

            services.AddAuthentication(options =>
                {
                    options.DefaultAuthenticateScheme = JwtBearerDefaults.AuthenticationScheme;
                    options.DefaultChallengeScheme = JwtBearerDefaults.AuthenticationScheme;
                    options.DefaultScheme = JwtBearerDefaults.AuthenticationScheme;
                })
                .AddJwtBearer(options =>
                {
                    options.SaveToken = true;
                    options.RequireHttpsMetadata = false;
                    options.TokenValidationParameters = new Microsoft.IdentityModel.Tokens.TokenValidationParameters()
                    {
                        ValidateIssuer = true,
                        ValidateAudience = true,
                        ValidAudience = "http://mydomain.com",
                        ValidIssuer = "http://mydomain.com",
                        IssuerSigningKey = new SymmetricSecurityKey(Encoding.UTF8.GetBytes("Secret 1234567890 phase"))
                    };
                });

            services.AddMvc().SetCompatibilityVersion(CompatibilityVersion.Version_2_1);
        }

        public void Configure(IApplicationBuilder app, IHostingEnvironment env)
        {
            if (env.IsDevelopment())
            {
                app.UseDeveloperExceptionPage();
            }

            app.UseAuthentication();

            app.UseMvc();
        }

EmployeeController.cs


[Route("api/[controller]")]
    [ApiController]
    [Authorize]
    public class EmployeeController : Controller
    {
        private readonly UserManager<IdentityUser> userManager;
        private readonly SignInManager<IdentityUser> signInManager;

        public EmployeeController(UserManager<IdentityUser> userManager, SignInManager<IdentityUser> signInManager)
        { 
            this.userManager = userManager;
            this.signInManager = signInManager;
        } 

        [HttpGet]
        public ActionResult<IEnumerable<string>> Get()
        {
            return userManager.Users.Select(u => u.UserName).ToArray();
        }

        [HttpPost]
        [AllowAnonymous]
        [Route("Register")]
        public async Task<JsonResult> Post(VMRegister vmRegister)
        {
            IdentityResult result = new IdentityResult();
            string errorMessage = "success";

            if (ModelState.IsValid)
            {
                var user = new IdentityUser
                {
                    UserName = vmRegister.EmailId,
                    Email = vmRegister.EmailId
                };

                result = await userManager.CreateAsync(user, vmRegister.Password);

                if (result.Succeeded)
                {
                    //to Signin user
                    //signInManager.SignInAsync(user, isPersistent: false).Start();
                }
                else
                {
                    if (result.Errors.Count() > 0)
                    {
                        errorMessage = "";
                        foreach (var error in result.Errors)
                        {
                            errorMessage += error.Description;
                        }
                    }
                }
            }

            return Json(new { id = "1", message = errorMessage });
        } 

        [HttpPost]
        [AllowAnonymous]
        [Route("Login")]
        public async Task<IActionResult> Login(VMLogin vmLogin)
        {
            var user = await userManager.FindByNameAsync(vmLogin.EmailId);
            if (user != null && await userManager.CheckPasswordAsync(user, vmLogin.Password))
            {
                var claims = new[]
                {
                    new Claim(JwtRegisteredClaimNames.Sub, user.UserName),
                    new Claim(JwtRegisteredClaimNames.Jti, Guid.NewGuid().ToString())
                };

                var signinKey = new SymmetricSecurityKey(Encoding.UTF8.GetBytes("Secret 1234567890 phase"));

                var token = new JwtSecurityToken(
                    issuer: "http://mydomain.com",
                    audience: "http://mydomain.com",
                    expires: DateTime.UtcNow.AddHours(1),
                    claims: claims,
                    signingCredentials: new Microsoft.IdentityModel.Tokens.SigningCredentials(signinKey, SecurityAlgorithms.HmacSha256)
                    );

                return Ok(
                    new
                    {
                        token = new JwtSecurityTokenHandler().WriteToken(token),
                        expiration = token.ValidTo
                    });
            }
            return Unauthorized();
        }  
    }

Testing












Hope this will help you and save your time.

Enjoy !!!

:)

.Net Core : Extend Identity User and add custom field in AspNetUsers table

.Net Core : Extend Identity User and add custom field in AspNetUsers table



Create new class and inherit with IdentityUser, here I created "ApplicationUser" and added 

namespace DotNetCodeDemo.Repository.Models
{
    public class ApplicationUser : IdentityUser
    {
        public string  City { get; set; }        
        public string MobileNumber { get; set; }
        public DateTime BirthDate { get; set; }
        public DateTime JoinDate { get; set; }
    }
}

Update dbContext class

namespace DotNetCodeDemo.Repository
{
    public class AppDbContext : IdentityDbContext<ApplicationUser>
    {
        public AppDbContext(DbContextOptions<AppDbContext> options) : base(options)
        {

        }

        public DbSet<Employee> Employees { get; set; }
        public DbSet<Department> Departments { get; set; }

        protected override void OnModelCreating(ModelBuilder modelBuilder)
        {
            base.OnModelCreating(modelBuilder);
            modelBuilder.Seed();
        }
    }
}

Update ConfigureServices method in startup class

public void ConfigureServices(IServiceCollection services)
{
 services.AddDbContextPool<AppDbContext>(options => options.UseSqlServer(Configuration.GetConnectionString("DotNetCoreDB")));

 services.AddIdentity<ApplicationUser, IdentityRole>(options =>
 {
  options.Password.RequiredLength = 10; // if you want to set your own password strength rule
  options.Password.RequiredUniqueChars = 2;
 }).AddEntityFrameworkStores<AppDbContext>(); 

 services.AddMvc().SetCompatibilityVersion(CompatibilityVersion.Version_2_1);
 services.AddScoped<IEmployeeRepository, EmployeeRepository>();
}

Update IdentityUser with ApplicationUser in your controller

namespace DotNetCodeDemo.Controllers
{
    [Route("api/[controller]")]
    [ApiController]
    public class AccountController : Controller
    {
        private readonly UserManager<ApplicationUser> userManager;
        private readonly SignInManager<ApplicationUser> signInManager;
        
        public AccountController(UserManager<ApplicationUser> userManager, SignInManager<ApplicationUser> signInManager)
        {
             
            this.userManager = userManager;
            this.signInManager = signInManager;
        }
         
        [HttpPost]
        [Route("Register")]
        public async Task<JsonResult> Post(VMRegister vmRegister)
        {
            IdentityResult result = new IdentityResult();
            string errorMessage = "success";

            if(ModelState.IsValid)
            {
                var user = new ApplicationUser
                {
                    UserName = vmRegister.Email,
                    Email = vmRegister.Email,
                    City = vmRegister.City
                };

                result = await userManager.CreateAsync(user, vmRegister.Password);

                if(result.Succeeded)
                {
                    //to Signin user
                    //signInManager.SignInAsync(user, isPersistent: false).Start();
                }
                else
                {
                    if(result.Errors.Count() > 0)
                    {
                        errorMessage = "";
                        foreach (var error in result.Errors)
                        {
                            errorMessage += error.Description;
                        }
                    }
                }
            }            

            return Json(new { id = "1", message = errorMessage });
        } 
    }
}

Hope this will help you and save your time.

Enjoy !!!

:)

.Net Core : AspNet Membership Login Method

.Net Core : AspNet Membership Login Method



AspNet membership login method code,

[HttpPost]
[Route("Login")]
public async Task<JsonResult> Post(VMLogin vmLogin)
{
Microsoft.AspNetCore.Identity.SignInResult result = new Microsoft.AspNetCore.Identity.SignInResult();
string errorMessage = "success";

if (ModelState.IsValid)
{
  
  result = await signInManager.PasswordSignInAsync(vmLogin.Email, vmLogin.Password, vmLogin.RememberMe, false);

if (!result.Succeeded)                 
{
errorMessage = "fail";
}
}

return Json(new { message = errorMessage });
} 



Hope this will help you and save your time.

Enjoy !!!

:)

.Net Core : Change Identity password complexity rules

.Net Core : Change Identity password complexity rules



Change Identity password complexity rules,


In ConfigureServices method

services.AddIdentity<IdentityUser, IdentityRole>(options =>
{
options.Password.RequiredLength = 10;
options.Password.RequiredUniqueChars = 2;
}).AddEntityFrameworkStores<AppDbContext>();


Hope this will help you and save your time.

Enjoy !!!

:)

.Net Core : Register User data into Identity table

.Net Core : Register User data into Identity table



Insert record in identity table,

namespace DotNetCoreDemo.Controllers
{
    [Route("api/[controller]")]
    [ApiController]
    public class AccountController : Controller
    {
        private readonly UserManager<IdentityUser> userManager;
        private readonly SignInManager<IdentityUser> signInManager;
        
        public AccountController(UserManager<IdentityUser> userManager, SignInManager<IdentityUser> signInManager)
        {
             
            this.userManager = userManager;
            this.signInManager = signInManager;
        }
         
        [HttpPost]
[Route("Register")]
        public async Task<JsonResult> Post(VMRegister vmRegister)
        {
            IdentityResult result = new IdentityResult();
            string errorMessage = "success";

            if(ModelState.IsValid)
            {
                var user = new IdentityUser
                {
                    UserName = vmRegister.Email,
                    Email = vmRegister.Email
                };

                result = await userManager.CreateAsync(user, vmRegister.Password);

                if(result.Succeeded)
                {
                    //to Signin user
                    //signInManager.SignInAsync(user, isPersistent: false).Start();
                }
                else
                {
                    if(result.Errors.Count() > 0)
                    {
                        errorMessage = "";
                        foreach (var error in result.Errors)
                        {
                            errorMessage += error.Description;
                        }
                    }
                }
            }            

            return Json(new { id = "1", message = errorMessage });
        } 
    }
}


Hope this will help you and save your time.

Enjoy !!!

:)

.Net Core : ASP.NET Membership - Identity User - Setup

.Net Core : ASP.NET Membership - Identity User - Setup



1. install nuget package - Microsoft.AspNetCore.Identity.EntityFrameworkCore

2. inherit DbContext class with IdentityDbContext
e.g., public class AppDbContext : IdentityDbContext

3.Configure identity in statup file, as below,
public void ConfigureServices(IServiceCollection services)
        {
            services.AddDbContextPool<AppDbContext>(options => options.UseSqlServer(Configuration.GetConnectionString("DotNetCoreDB")));

            services.AddIdentity<IdentityUser, IdentityRole>()
                    .AddEntityFrameworkStores<AppDbContext>();

            services.AddMvc().SetCompatibilityVersion(CompatibilityVersion.Version_2_1);
            services.AddScoped<IEmployeeRepository, EmployeeRepository>();
        }

4. add "app.UseAuthentication();" in Configure method before "app.UseMvc();".

5. Do datamigration using
Add-Migration "AddIdentity"

6. If you will get error like "The entity type 'IdentityUserLogin<string>' requires a primary key to be defined."
then 
goto appDbContext class and do changes in OnModelCreating method as below,
base.OnModelCreating(modelBuilder);

7. Now run again Add-Migration "AddIdentity"

8. then run Update-Database

9. Finally you can see there are some tables name start with "ASPNet" are added in database.

Hope this will help you and save your time.

Enjoy !!!

:)

Azure : LogicApp If Condition

Azure : LogicApp If Condition



Here is sample code to send email using Azure function app

API Response

body
{
    "ResultCode": "OK",
    "Message": "Success",
    "Data": "demo@gmail.com"
}

If Condition Step, get http API response result value, Here we are getting above result and want to get value of "ResultCode", and based on we need to perform another action, so we can get it as below,



 "expression": {
 "and": [
  {
  "equals": [
   "@outputs('HttpStepName')['body']?['ResultCode']",
   "OK"
  ]
  }
 ]
},


Hope this will help you and save your time.

Enjoy !!!

:)