this is the image of the problem.
my login function in the API
public async Task<object> Login([FromBody] LoginDto model)
{
var user = _context.Users.FirstOrDefault(x => x.Email == model.Email || x.UserName == model.Email);
var result = await _signInManager.PasswordSignInAsync(user.UserName, model.Password, model.RememberMe, false);
var IsAuthenticate = User.Identity.IsAuthenticated;
await _signInManager.SignInAsync(user, model.RememberMe);
if (result.Succeeded)
{
var appUser = _userManager.Users.SingleOrDefault(r => r.Email == model.Email);
return await GenerateJwtToken(model.Email, appUser);
}
return BadRequest("INVALID_LOGIN_ATTEMPT");
}
my login function in MVC with consume API _client.LoginAsync() is a static function to consume API for login
public async Task<IActionResult> Login(LoginDto model, string returnUrl = null)
{
ViewData["ReturnUrl"] = returnUrl;
if (ModelState.IsValid)
{
try
{
await _client.LoginAsync<LoginDto>(new Uri(_appSettings.WebApiBaseUrl + "Account/Login"), model);
ApplicationManager.SetMessageToUser("تم تسجيل الدخول بمجاح");
await _signInManager.PasswordSignInAsync(model.Email, model.Password, model.RememberMe, false);
return Redirect("/" + returnUrl);
}
catch
{
}
}
ApplicationManager.SetMessageToUser("تأكد من اسم المستخدم وكلمة المرور");
// If we got this far, something failed, redisplay form
return View(model);
}
_client.LoginAsync() is a function to consume api for login
public async Task<string> LoginAsync<T>(Uri requestUrl, T content)
{
addHeaders();
var response = await _httpClient.PostAsync(requestUrl.ToString(), CreateHttpContent<T>(content));
string st = response.Content.ReadAsStringAsync().Result;
response.EnsureSuccessStatusCode();
var data = await response.Content.ReadAsStringAsync();
return (string)data;
}
my configuration for services
public void ConfigureServices(IServiceCollection services)
{
services.AddSession(options => {
options.IdleTimeout = TimeSpan.FromMinutes(60);
});
services.Configure<AppSettings>(Configuration.GetSection("AppSettings"));
services.AddDbContext<ApplicationDbContext>(opt =>
opt.UseSqlServer("Data Source=.;Initial Catalog=ECommerceWebDb;Integrated Security=True"));
services.AddIdentity<IdentityUser, IdentityRole>(options =>
{
options.Password.RequireNonAlphanumeric = false;
options.Password.RequiredLength = 8;
options.User.RequireUniqueEmail = true;
})
.AddEntityFrameworkStores<ApplicationDbContext>()
.AddDefaultTokenProviders();
services.AddControllers();
services.AddCors();
services.AddMvc();
services.AddControllersWithViews();
services.AddRazorPages();
var appSettingsSection = Configuration.GetSection("AppSettings");
services.Configure<AppSettings>(appSettingsSection);
// configure jwt authentication
var appSettings = appSettingsSection.Get<AppSettings>();
var key = Encoding.ASCII.GetBytes(appSettings.Secret);
services.AddAuthentication(x =>
{
x.DefaultAuthenticateScheme = JwtBearerDefaults.AuthenticationScheme;
x.DefaultChallengeScheme = JwtBearerDefaults.AuthenticationScheme;
})
.AddJwtBearer(x =>
{
x.RequireHttpsMetadata = false;
x.SaveToken = true;
x.TokenValidationParameters = new TokenValidationParameters
{
ValidateIssuerSigningKey = true,
IssuerSigningKey = new SymmetricSecurityKey(key),
ValidateIssuer = false,
ValidateAudience = false
};
});
}
// 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.UseCors();
app.UseAuthentication();
app.UseAuthorization();
app.UseEndpoints(endpoints =>
{
endpoints.MapControllerRoute(
name: "default",
pattern: "{controller=Home}/{action=Index}/{id?}");
endpoints.MapAreaControllerRoute(
name: "areas", "areas",
pattern: "{area:exists}/{controller=Home}/{action=Index}/{id?}");
endpoints.MapRazorPages();
});
}
I complicated with this error I think this is everything if you want more to help me please tell me.
I found the solve
if you face the same problem JWT does not support cookies with tokens together so you must remove
x.DefaultAuthenticateScheme = JwtBearerDefaults.AuthenticationScheme;
x.DefaultChallengeScheme = JwtBearerDefaults.AuthenticationScheme;
from services.AddAuthentication
services.AddAuthentication(x =>
{
})
.AddJwtBearer(x =>
{
x.RequireHttpsMetadata = false;
x.SaveToken = true;
x.TokenValidationParameters = new TokenValidationParameters
{
ValidateIssuerSigningKey = true,
IssuerSigningKey = new SymmetricSecurityKey(key),
ValidateIssuer = false,
ValidateAudience = false
};
});
when you need to authorize any action by token you can use this attribute
[Authorize(AuthenticationSchemes = JwtBearerDefaults.AuthenticationScheme)]
to any actions.
when you need to authorize any action by cookie you need to add
[Authorize]