Reputation: 1223
EDIT: So After many failed attempts to figure out why this is not working I decided to create a project and choose to have user login implemented from there so it will configure everything for me. after that I just scraped the automated login/register code and replaced it with my own. everything works amazingly well. I am pretty sure in my original version I missed some needed parameter
I am trying to make a simple login function. but I cant seem to get it to work and it drives me crazy ..
so I do my shared folder under _layout.cshtml I have added this
@inject SignInManager<IdentityUser> signInManager;
and then just a little later inside my navbar I added this elements
<ul class="navbar-nav ml-auto">
@if (signInManager.IsSignedIn(User)) {
<li class="nav-item">
<form method="post" asp-controller="User" asp-action="Logout">
<button type="submit" class="nav-link btn btn-link py-0" style="width:auto">
Logout @User.Identity.Name
</button>
</form>
</li>
}
else {
<li class="nav-item">
<a class="nav-link text-dark" asp-area="" asp-controller="User" asp-action="Register">Register</a>
</li>
<li class="nav-item">
<a class="nav-link text-dark" asp-area="" asp-controller="User" asp-action="Login">Login</a>
</li>
}
</ul>
and in my controller I added this I called this controller UserController.cs If I enter wrong login info . like wrong password or username it will tell me I that. so the connection with the database is no issue. but when I am send in my "Home" Index I am not logged it. as if it does not create a session I am not sure
[HttpGet]
public IActionResult Login()
{
return View();
}
[HttpPost]
public async Task<IActionResult> Login(Login model)
{
if (ModelState.IsValid)
{
var result = await signInManager.PasswordSignInAsync(model.UserName,model.Password,
model.RememberMe,false);
if (result.Succeeded)
{
//creates a temponary sign in session cookie. that cookie is going to be lost after the browser is closed
return RedirectToAction("index", "home");
}
//if succeeded = false then ew llop through the error list
ModelState.AddModelError(string.Empty,"Invalid Login");
}
return View(model);
}
Upvotes: 0
Views: 194
Reputation: 36645
Here is the whole working demo like below:
View(Login.cshtml):
@using Microsoft.AspNetCore.Identity
@model LoginViewModel
@inject SignInManager<IdentityUser> SignInManager
@{
ViewData["Title"] = "Log in";
}
<h1>@ViewData["Title"].</h1>
<div class="row">
<div class="col-md-8">
<section>
<form asp-controller="Account" asp-action="Login" asp-route-returnurl="@ViewData["ReturnUrl"]" method="post" class="form-horizontal" role="form">
<h4>Use a local account to log in.</h4>
<hr />
<div asp-validation-summary="All" class="text-danger"></div>
<div class="form-group">
<label asp-for="Email" class="col-md-2 control-label"></label>
<div class="col-md-10">
<input asp-for="Email" class="form-control" />
<span asp-validation-for="Email" class="text-danger"></span>
</div>
</div>
<div class="form-group">
<label asp-for="Password" class="col-md-2 control-label"></label>
<div class="col-md-10">
<input asp-for="Password" class="form-control" />
<span asp-validation-for="Password" class="text-danger"></span>
</div>
</div>
<div class="form-group">
<div class="col-md-offset-2 col-md-10">
<div class="checkbox">
<label asp-for="RememberMe">
<input asp-for="RememberMe" />
@Html.DisplayNameFor(m => m.RememberMe)
</label>
</div>
</div>
</div>
<div class="form-group">
<div class="col-md-offset-2 col-md-10">
<button type="submit" class="btn btn-default">Log in</button>
</div>
</div>
<p>
<a asp-action="Register" asp-route-returnurl="@ViewData["ReturnUrl"]">Register as a new user?</a>
</p>
<p>
<a asp-action="ForgotPassword">Forgot your password?</a>
</p>
</form>
</section>
</div>
<div class="col-md-4">
<section>
<h4>Use another service to log in.</h4>
<hr />
@{
var schemes = await SignInManager.GetExternalAuthenticationSchemesAsync();
var loginProviders = schemes.ToList();
if (loginProviders.Count == 0)
{
<div>
<p>
There are no external authentication services configured. See <a href="http://go.microsoft.com/fwlink/?LinkID=532715">this article</a>
for details on setting up this ASP.NET application to support logging in via external services.
</p>
</div>
}
else
{
<form asp-controller="Account" asp-action="ExternalLogin" asp-route-returnurl="@ViewData["ReturnUrl"]" method="post" class="form-horizontal" role="form">
<div>
<p>
@foreach (var provider in loginProviders)
{
<button type="submit" class="btn btn-default" name="provider" value="@provider.Name" title="Log in using your @provider.Name account">@provider.Name</button>
}
</p>
</div>
</form>
}
}
</section>
</div>
</div>
@section Scripts {
@{ await Html.RenderPartialAsync("_ValidationScriptsPartial"); }
}
Controller:
[Authorize]
public class AccountController : Controller
{
private readonly UserManager<IdentityUser> _userManager;
private readonly SignInManager<IdentityUser> _signInManager;
public AccountController(
UserManager<IdentityUser> userManager,
SignInManager<IdentityUser> signInManager)
{
_userManager = userManager;
_signInManager = signInManager;
}
// GET: /Account/Login
[HttpGet]
[AllowAnonymous]
public IActionResult Login()
{
return View();
}
// POST: /Account/Login
[HttpPost]
[AllowAnonymous]
[ValidateAntiForgeryToken]
public async Task<IActionResult> Login(LoginViewModel model)
{
if (ModelState.IsValid)
{
var result = await _signInManager.PasswordSignInAsync(model.Email, model.Password, model.RememberMe, lockoutOnFailure: false);
if (result.Succeeded)
{
return RedirectToAction("Index", "Home");
}
else
{
ModelState.AddModelError(string.Empty, "Invalid login attempt.");
return View(model);
}
}
return View(model);
}
}
DbContext:
public class ApplicationDbContext : IdentityDbContext
{
public ApplicationDbContext(DbContextOptions options) : base(options) { }
}
Startup.cs
public class Startup
{
public Startup(IConfiguration configuration)
{
Configuration = configuration;
}
public IConfiguration Configuration { get; }
// This method gets called by the runtime. Use this method to add services to the container.
public void ConfigureServices(IServiceCollection services)
{
services.AddControllersWithViews();
services.AddDbContext<ApplicationDbContext>(options =>
options.UseSqlServer(Configuration.GetConnectionString("DefaultConnection")));
services.AddIdentityCore<IdentityUser>()
.AddEntityFrameworkStores<ApplicationDbContext>()
.AddSignInManager()
.AddDefaultTokenProviders();
services.AddAuthentication(o =>
{
o.DefaultScheme = IdentityConstants.ApplicationScheme;
o.DefaultSignInScheme = IdentityConstants.ExternalScheme;
})
.AddIdentityCookies(o => { });
}
// This method gets called by the runtime. Use this method to configure the HTTP request pipeline.
public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
{
if (env.IsDevelopment())
{
app.UseDeveloperExceptionPage();
}
else
{
app.UseExceptionHandler("/Home/Error");
// The default HSTS value is 30 days. You may want to change this for production scenarios, see https://aka.ms/aspnetcore-hsts.
app.UseHsts();
}
app.UseHttpsRedirection();
app.UseStaticFiles();
app.UseRouting();
app.UseAuthentication();
app.UseAuthorization();
app.UseEndpoints(endpoints =>
{
endpoints.MapControllerRoute(
name: "default",
pattern: "{controller=Home}/{action=Index}/{id?}");
});
}
}
Upvotes: 1