Introduction
Authentication is the process of determining or giving an individual access to system or user based on their identity. There are multiple options to do authentication in .NET Core. This article demonstrates how to add cookie based authentication in .NET Core 3.0.
With .NET Core 3.0, you can use cookie-based authentication out of the box without adding new additional NuGet packages.
Prerequisites
- Install .NET Core 3.0.0 or above SDK from here. Install the latest version of Visual Studio 2019 Community Edition from here.
Steps for Creating a Web Application
- Go to Visual Studio 2019, then select Create new project option from option list:
- After selecting that, a new window will open to select project template.
- Select “ASP.NET Core Web Application” and click on Next button.
- A new screen will open to configure your new project. Provide Project Name, Location, Solution Name as per your requirement. Press Create button.
- After clicking on Create button, a new screen will open to configure your project related information like which environment you want create for web application? .NET Framework or .NET Core. Select .NET Core and ASP.NET Core Version from drop down list. Then, select web application (Model-View-Controller) option from list and press Create button to create a project.
Now our project will open with basic structure of .NET Core environment. You can observe in the Solution Explorer that will have Controllers, Models and Views folders with “Startup.cs” and other files as well like the image below:
- Run your application to check whether the created web application is running fine or not. By default, it will open a Home page (Index page of Home controller) of your project.
Integrate Cookie Authentication
[Authorize]
: attribute helps to validate user to an access controller (User Information) Claim
: Contained user related information which will be stored into cookie ClaimsIdentity
: Pass list of claim and AuthenticationType
ClaimsPrincipal
: Accept an array of ClaimsIdentity
SignInAsync
: Pass ClaimsPrinciple
to it as parameter and finally, this method will create a cookie into browser
Startup.cs file Code Changes
- Open “Startup.cs” file and add
AddAuthentication
service into ConfigureServices
method like below. Provide login path to login user to check/verify user is valid or not.
1 public void ConfigureServices(IServiceCollection services)
2 {
3 services.AddAuthentication("CookieAuthentication")
4 .AddCookie("CookieAuthentication", config =>
5 {
6 config.Cookie.Name = "UserLoginCookie";
7 config.LoginPath = "/Login/UserLogin";
8 });
9
10 services.AddControllersWithViews();
11 }
- Add
UseAuthentication
and UseAuthorization
extension method into Configure
method of “Startup.cs”.
UseAuthentication
: Helps us to check “Who are you?”
UseAuthorization
: Helps to check “Are you allowed to access an information?”
- Complete code in Startup.cs file:
1 using System;
2 using System.Collections.Generic;
3 using System.Linq;
4 using System.Threading.Tasks;
5 using Microsoft.AspNetCore.Builder;
6 using Microsoft.AspNetCore.Hosting;
7 using Microsoft.AspNetCore.HttpsPolicy;
8 using Microsoft.Extensions.Configuration;
9 using Microsoft.Extensions.DependencyInjection;
10 using Microsoft.Extensions.Hosting;
11
12 namespace CookieAuthenticationDemo
13 {
14 public class Startup
15 {
16 public Startup(IConfiguration configuration)
17 {
18 Configuration = configuration;
19 }
20
21 public IConfiguration Configuration { get; }
22
23
24
25 public void ConfigureServices(IServiceCollection services)
26 {
27 services.AddAuthentication("CookieAuthentication")
28 .AddCookie("CookieAuthentication", config =>
29 {
30 config.Cookie.Name = "UserLoginCookie";
31 config.LoginPath = "/Login/UserLogin";
32 });
33
34 services.AddControllersWithViews();
35 }
36
37
38
39 public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
40 {
41 if (env.IsDevelopment())
42 {
43 app.UseDeveloperExceptionPage();
44 }
45 else
46 {
47 app.UseExceptionHandler("/Home/Error");
48
49
50
51 app.UseHsts();
52 }
53 app.UseHttpsRedirection();
54 app.UseStaticFiles();
55
56 app.UseRouting();
57
58
59 app.UseAuthentication();
60
61
62 app.UseAuthorization();
63
64 app.UseEndpoints(endpoints =>
65 {
66 endpoints.MapControllerRoute(
67 name: "default",
68 pattern: "{controller=Home}/{action=Index}/{id?}");
69 });
70 }
71 }
72 }
Add User.cs File into Model Folder
Add new class into Models folder with name Users
and put the below lines of code into it:
1 using System.Collections.Generic;
2
3 namespace CookieAuthenticationDemo.Models
4 {
5 public class Users
6 {
7 public int Id { get; set; }
8 public string UserName { get; set; }
9 public string Name { get; set; }
10 public string EmailId { get; set; }
11 public string Password { get; set; }
12
13 public IEnumerable<Users> GetUsers()
14 {
15 return new List<Users>() { new Users
16 { Id = 101, UserName = "anet", Name = "Anet",
17 EmailId = "anet@test.com", Password = "anet123" } };
18 }
19 }
20 }
Update HomeController with New Action Method
HomeController
is the default controller created by Visual Studio while creating a new project.
- Add a new action method into
HomeController
to get list of users with Authorize
attribute.
using CookieAuthenticationDemo.Models;
using Microsoft.AspNetCore.Authorization;
using Microsoft.AspNetCore.Mvc;
namespace CookieAuthenticationDemo.Controllers
{
public class HomeController : Controller
{
public IActionResult Index()
{
return View();
}
[Authorize]
public ActionResult Users()
{
var uses = new Users();
return View(uses.GetUsers());
}
}
}
- Add view for Users:
- Go to Views folder and select Home folder
- Right click on the Home folder to select add option and select view.
- A window popup will open to add View.
- Provide View name as User, select Template as Empty, select Use a layout page and press Add button. A new Users.cshtml file will create into Home folder. Refer to the image below to add view:
Put the below lines of code into it to show list of users:
1 @model IEnumerable<CookieAuthenticationDemo.Models.Users>
2
3 @{
4 ViewData["Title"] = "Users";
5 }
6
7 <h1>Users</h1>
8 <table class="table">
9 <thead>
10 <tr>
11 <th>
12 @Html.DisplayNameFor(model => model.Id)
13 </th>
14 <th>
15 @Html.DisplayNameFor(model => model.UserName)
16 </th>
17 <th>
18 @Html.DisplayNameFor(model => model.Name)
19 </th>
20 <th>
21 @Html.DisplayNameFor(model => model.EmailId)
22 </th>
23 <th></th>
24 </tr>
25 </thead>
26 <tbody>
27 @foreach (var item in Model) {
28 <tr>
29 <td>
30 @Html.DisplayFor(modelItem => item.Id)
31 </td>
32 <td>
33 @Html.DisplayFor(modelItem => item.UserName)
34 </td>
35 <td>
36 @Html.DisplayFor(modelItem => item.Name)
37 </td>
38 <td>
39 @Html.DisplayFor(modelItem => item.EmailId)
40 </td>
41 </tr>
42 }
43 </tbody>
44 </table>
Add New Controller With Name Login
- Right click on controllers folder
- Select Add, then select Controller and then select MVC empty controller and click on Add button.
- Add controller with name Login as “LoginController”
- Add the below code into that controller:
1 using CookieAuthenticationDemo.Models;
2 using Microsoft.AspNetCore.Authentication;
3 using Microsoft.AspNetCore.Mvc;
4 using System.Collections.Generic;
5 using System.Linq;
6 using System.Security.Claims;
7
8 namespace CookieAuthenticationDemo.Controllers
9 {
10 public class LoginController : Controller
11 {
12 [HttpGet]
13 public ActionResult UserLogin()
14 {
15 return View();
16 }
17
18 [HttpPost]
19 public ActionResult UserLogin([Bind] Users user)
20 {
21
22 var users = new Users();
23 var allUsers = users.GetUsers().FirstOrDefault();
24 if (users.GetUsers().Any(u => u.UserName == user.UserName ))
25 {
26 var userClaims = new List<Claim>()
27 {
28 new Claim(ClaimTypes.Name, user.UserName),
29 new Claim(ClaimTypes.Email, "anet@test.com"),
30 };
31
32 var grandmaIdentity =
33 new ClaimsIdentity(userClaims, "User Identity");
34
35 var userPrincipal = new ClaimsPrincipal(new[] { grandmaIdentity });
36 HttpContext.SignInAsync(userPrincipal);
37
38 return RedirectToAction("Index", "Home");
39 }
40
41 return View(user);
42 }
43 }
44 }
- Add a
UserLogin.cshtml(UserLogin view)
page:
- Add new folder into Views folder with name
User
. - Add
UserLogin
into User folder and add the below lines of code into it to user login:
Code for UserLogin.cshtml:
1 @model CookieAuthenticationDemo.Models.Users
2
3 @{
4 ViewData["Title"] = "User Login";
5 }
6
7 <hr />
8 <div class="row">
9 <div class="col-md-4">
10 <form asp-action="UserLogin">
11 <h2>User Login</h2>
12 <div asp-validation-summary="ModelOnly" class="text-danger"></div>
13 <div class="form-group">
14 <label asp-for="UserName" class="control-label"></label>
15 <input asp-for="UserName" class="form-control" />
16 <span asp-validation-for="UserName" class="text-danger"></span>
17 </div>
18 <div class="form-group">
19 <label asp-for="Password" class="control-label"></label>
20 <input type="password" asp-for="Password"
21
22 class="form-control" />
23 <span asp-validation-for="Password" class="text-danger"></span>
24 </div>
25 <div class="form-group">
26 <input type="submit" value="Login"
27
28 class="btn btn-default btn-primary" />
29 </div>
30 </form>
31 </div>
32 </div>
Update _Layout.cshtml Page
Update _Layout.cshtml page to add new tab/hyperlink to get list of users.
Code for _Layout.cshtml is as follows:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8" />
<meta name="viewport"
content="width=device-width, initial-scale=1.0" />
<title>@ViewData["Title"] - CookieAuthenticationDemo</title>
<link rel="stylesheet"
href="~/lib/bootstrap/dist/css/bootstrap.min.css" />
<link rel="stylesheet" href="~/css/site.css" />
</head>
<body>
<header>
<nav class="navbar navbar-expand-sm
navbar-toggleable-sm navbar-light bg-white border-bottom box-shadow mb-3">
<div class="container">
<a class="navbar-brand" asp-area=""
asp-controller="Home"
asp-action="Index">CookieAuthenticationDemo</a>
<button class="navbar-toggler" type="button"
data-toggle="collapse"
data-target=".navbar-collapse"
aria-controls="navbarSupportedContent"
aria-expanded="false" aria-label="Toggle navigation">
<span class="navbar-toggler-icon"></span>
</button>
<div class="navbar-collapse
collapse d-sm-inline-flex flex-sm-row-reverse">
<ul class="navbar-nav flex-grow-1">
<li class="nav-item">
<a class="nav-link text-dark"
asp-area="" asp-controller="Home"
asp-action="Index">Home</a>
</li>
<li class="nav-item">
<a class="nav-link text-dark"
asp-area="" asp-controller="Home"
asp-action="Users">Users</a>
</li>
</ul>
</div>
</div>
</nav>
</header>
<div class="container">
<main role="main" class="pb-3">
@RenderBody()
</main>
</div>
<footer class="border-top footer text-muted">
<div class="container">
© 2020 - CookieAuthenticationDemo - <a asp-area=""
asp-controller="Home" asp-action="Privacy">Privacy</a>
</div>
</footer>
<script src="~/lib/jquery/dist/jquery.min.js"></script>
<script src="~/lib/bootstrap/dist/js/bootstrap.bundle.min.js"></script>
<script src="~/js/site.js" asp-append-version="true"></script>
@RenderSection("Scripts", required: false)
</body>
</html>
Run Your Application
After successfully running your application, output of your application should be like the screen below:
Click on Users tab to get list of users, it will open a login page to login a user.
Question: Why will it ask for login?
Answer: [Authorize]
attribute restricts to access data/information for unauthorized requests and redirects to login page to check whether user is valid or not. In our case, we have added this attribute over the Users action method of HomeController
.
Provide username and password to login. After login, it will create a cookie in the browser like below:
Click on the Users tab again and now you can find the final result of user list without asking for login screen.
To test your cookie based authentication, you can delete that created cookie from browser and click on the Users tab. It will ask for login again.
Summary
In this article, I discussed how to add cookie based authentication in .NET Core 3.0. We have also created a user login form to login a user to our application to access useful information. Please find the attached code for better understanding.
History
- 14th January, 2020: Initial version