ASPNET ID 2.0에서 사용자 사용 안 함
시스템에서 사용자를 삭제하는 대신 사용자를 비활성화하는 방법을 찾고 있습니다. 이는 관련 데이터의 데이터 무결성을 유지하기 위한 것입니다.하지만 ASPNET ID는 계정 삭제만 제공하는 것 같습니다.
새로운 잠금 기능이 있지만 잠금을 제어하여 사용자를 비활성화할 수 있지만 특정 횟수의 잘못된 암호 시도 후에만 사용자를 잠글 수 있습니다.
다른 방법은?
ID 비트가 설치된 사이트를 만들면 "IdentityModels.cs "이라는 파일이 사이트에 나타납니다.이 파일에는 IdentityUser에서 상속되는 ApplicationUser라는 클래스가 있습니다.
// You can add profile data for the user by adding more properties to your ApplicationUser class, please visit https://devblogs.microsoft.com/aspnet/customizing-profile-information-in-asp-net-identity-in-vs-2013-templates/ to learn more.
public class ApplicationUser : IdentityUser
여기를 쉽게 클릭할 수 있도록 댓글에 멋진 링크가 있습니다.
이 자습서에서는 사용자에 대한 사용자 지정 속성을 추가하기 위해 수행해야 하는 작업에 대해 정확하게 설명합니다.
그리고 실제로, 튜토리얼을 보는 것조차 없습니다.
ApplicationUser 클래스에 속성 추가(예:
공공장소에서?사용 여부{ get; set; }
DB의 AsNetUsers 테이블에 동일한 이름의 열을 추가합니다.
쾅, 바로 그거야!
이제 계정 컨트롤러에서 다음과 같은 등록 작업이 수행됩니다.
public async Task<ActionResult> Register(RegisterViewModel model)
{
if (ModelState.IsValid)
{
var user = new ApplicationUser { UserName = model.Email, Email = model.Email, IsEnabled = true };
var result = await UserManager.CreateAsync(user, model.Password);
if (result.Succeeded)
ApplicationUser 개체를 만들 때 IsEnabled = true를 추가했습니다.이제 값이 AsNetUsers 테이블의 새 열에 유지됩니다.
그런 다음 ApplicationSignInManager에서 PasswordSignInAsync를 재정의하여 로그인 프로세스의 일부로 이 값을 확인해야 합니다.
저는 다음과 같이 했습니다.
public override Task<SignInStatus> PasswordSignInAsync(string userName, string password, bool rememberMe, bool shouldLockout)
{
var user = UserManager.FindByEmailAsync(userName).Result;
if ((user.IsEnabled.HasValue && !user.IsEnabled.Value) || !user.IsEnabled.HasValue)
{
return Task.FromResult<SignInStatus>(SignInStatus.LockedOut);
}
return base.PasswordSignInAsync(userName, password, rememberMe, shouldLockout);
}
마일리지는 다양할 수 있으며, 해당 SignIn Status를 반환하고 싶지 않을 수도 있지만, 이해할 수 있습니다.
은 " " 입니다.LockoutEnabled
의 User
사용자가 현재 잠겨 있는지 여부를 나타내는 속성이 아닙니다.가 한 AccessFailedCount
에 합니다.MaxFailedAccessAttemptsBeforeLockout
value.를 값 차단하는 일 뿐입니다.LockedoutEnddateUtc
중단하려면 속성을 사용해야 따라서 사용자 계정을 영구적으로 사용하지 않도록 설정하거나 일시 중단하려면 사용자 고유의 플래그 속성을 도입해야 할 수 있습니다.
사용자 지정 속성을 생성할 필요가 없습니다.비결은 다음을 설정하는 것입니다.LockoutEnabled
의 속성 및 합니다.LockoutoutEndDateUtc
사용자를 잠그기 위해 코드에서 미래 날짜까지.그리고 나서, 전화를 겁니다.UserManager.IsLockedOutAsync(user.Id
합니다. ) false를 반환합니다.
다 둘다LockoutEnabled
그리고.LockoutoutEndDateUtc
사용자를 잠그려면 실제 날짜 및 미래 날짜 기준을 충족해야 합니다.예를 들어, 다음과 같은 경우.LockoutoutEndDateUtc
은 은입니다.2014-01-01 00:00:00.000
그리고.LockoutEnabled
이라true
을 부르기UserManager.IsLockedOutAsync(user.Id)
여전히 돌아올 것입니다.true
Microsoft에서 사용자가 잠기는 시간에 대한 시간 범위를 설정할 수 있도록 이러한 방법을 설계한 이유를 알 수 있습니다.
하지만, 나는 그것이 되어야 한다고 주장할 것입니다.LockoutEnabled
이라true
합니다.LockoutoutEndDateUtc
NULL이거나 이후 날짜입니다.두 속성을 설정하는 가 없습니다.LockoutoutEndDateUtc
이라NULL
기본값).당신은 그냥 설정할 수 있습니다.LockoutEnabled
true
그리고 만약에LockoutoutEndDateUtc
이라NULL
사용자가 무기한으로 잠겼습니다.
사용자 지정 IdentityUser 파생 클래스에 사용자 고유의 플래그를 삽입하고 사용/사용 안 함 및 사용자가 사용하지 않을 경우 로그인하지 못하도록 하는 사용자 고유의 논리를 구현/시행해야 합니다.
제가 실제로 한 일은 이것뿐입니다.
var lockoutEndDate = new DateTime(2999,01,01);
UserManager.SetLockoutEnabled(userId,true);
UserManager.SetLockoutEndDate(userId, lockoutEndDate);
이는 기본적으로 잠금을 사용 가능으로 설정하는 것입니다(기본적으로 이 작업을 아직 수행하지 않은 경우). 잠금 종료 날짜를 먼 값으로 설정합니다.
Ozz가 맞지만 기본 클래스를 보고 모든 사인 각도에 대해 확인할 수 있는 방법을 찾는 것이 좋을 수 있습니다. CanSignIn일 수도 있다고 생각합니다.
MS가 오픈 소스이기 때문에 이제 MS의 구현을 확인할 수 있습니다.
https://github.com/aspnet/AspNetCore/blob/master/src/Identity/src/Identity/SignInManager.cs
(URL이 다음으로 변경됨:
https://github.com/aspnet/AspNetCore/blob/master/src/Identity/Core/src/SignInManager.cs)
public class CustomSignInManager : SignInManager<ApplicationUser>
{
public CustomSignInManager(UserManager<ApplicationUser> userManager,
IHttpContextAccessor contextAccessor,
IUserClaimsPrincipalFactory<ApplicationUser> claimsFactory,
IOptions<IdentityOptions> optionsAccessor,
ILogger<SignInManager<ApplicationUser>> logger,
IAuthenticationSchemeProvider schemes) : base(userManager, contextAccessor, claimsFactory, optionsAccessor, logger, schemes)
{
}
public override async Task<bool> CanSignInAsync(ApplicationUser user)
{
if (Options.SignIn.RequireConfirmedEmail && !(await UserManager.IsEmailConfirmedAsync(user)))
{
Logger.LogWarning(0, "User {userId} cannot sign in without a confirmed email.", await UserManager.GetUserIdAsync(user));
return false;
}
if (Options.SignIn.RequireConfirmedPhoneNumber && !(await UserManager.IsPhoneNumberConfirmedAsync(user)))
{
Logger.LogWarning(1, "User {userId} cannot sign in without a confirmed phone number.", await UserManager.GetUserIdAsync(user));
return false;
}
if (UserManager.FindByIdAsync(user.Id).Result.IsEnabled == false)
{
Logger.LogWarning(1, "User {userId} cannot sign because it's currently disabled", await UserManager.GetUserIdAsync(user));
return false;
}
return true;
}
}
또한 CanSignIn을 호출하는 PreSignInCheck를 재정의하는 것도 고려해 보십시오.
protected virtual async Task<SignInResult> PreSignInCheck(TUser user)
{
if (!await CanSignInAsync(user))
{
return SignInResult.NotAllowed;
}
if (await IsLockedOut(user))
{
return await LockedOut(user);
}
return null;
}
이 클래스를 사용할 수 있습니다...ASP의 깨끗한 구현.NET ID...내 코드야.기본 키에 대한 int는 기본 키에 대한 다른 유형을 원한다면 변경할 수 있습니다.
IdentityConfig.cs
public class ApplicationUserManager : UserManager<ApplicationUser, int>
{
public ApplicationUserManager(IUserStore<ApplicationUser, int> store)
: base(store)
{
}
public static ApplicationUserManager Create(IdentityFactoryOptions<ApplicationUserManager> options, IOwinContext context)
{
var manager = new ApplicationUserManager(new ApplicationUserStore(context.Get<ApplicationContext>()));
manager.UserValidator = new UserValidator<ApplicationUser, int>(manager)
{
AllowOnlyAlphanumericUserNames = false,
RequireUniqueEmail = true
};
manager.PasswordValidator = new PasswordValidator
{
RequiredLength = 6,
RequireNonLetterOrDigit = true,
RequireDigit = true,
RequireLowercase = true,
RequireUppercase = true,
};
manager.UserLockoutEnabledByDefault = false;
var dataProtectionProvider = options.DataProtectionProvider;
if (dataProtectionProvider != null)
{
manager.UserTokenProvider =
new DataProtectorTokenProvider<ApplicationUser, int>(
dataProtectionProvider.Create("ASP.NET Identity"));
}
return manager;
}
}
public class ApplicationSignInManager : SignInManager<ApplicationUser, int>
{
public ApplicationSignInManager(ApplicationUserManager userManager, IAuthenticationManager authenticationManager) :
base(userManager, authenticationManager) { }
public override Task<ClaimsIdentity> CreateUserIdentityAsync(ApplicationUser user)
{
return user.GenerateUserIdentityAsync((ApplicationUserManager)UserManager);
}
public static ApplicationSignInManager Create(IdentityFactoryOptions<ApplicationSignInManager> options, IOwinContext context)
{
return new ApplicationSignInManager(context.GetUserManager<ApplicationUserManager>(), context.Authentication);
}
}
public class ApplicationRoleManager : RoleManager<ApplicationRole, int>
{
public ApplicationRoleManager(IRoleStore<ApplicationRole, int> store)
: base(store)
{
}
}
public class ApplicationRoleStore : RoleStore<ApplicationRole, int, ApplicationUserRole>
{
public ApplicationRoleStore(ApplicationContext db)
: base(db)
{
}
}
public class ApplicationUserStore : UserStore<ApplicationUser, ApplicationRole, int,
ApplicationLogin, ApplicationUserRole, ApplicationClaim>
{
public ApplicationUserStore(ApplicationContext db)
: base(db)
{
}
}
IdentityModel.cs
public class ApplicationUser : IdentityUser<int, ApplicationLogin, ApplicationUserRole, ApplicationClaim>
{
//your property
//flag for users state (active, deactive or enabled, disabled)
//set it false to disable users
public bool IsActive { get; set; }
public ApplicationUser()
{
}
public async Task<ClaimsIdentity> GenerateUserIdentityAsync(UserManager<ApplicationUser, int> manager)
{
var userIdentity = await manager.CreateIdentityAsync(this, DefaultAuthenticationTypes.ApplicationCookie);
return userIdentity;
}
}
public class ApplicationUserRole : IdentityUserRole<int>
{
}
public class ApplicationLogin : IdentityUserLogin<int>
{
public virtual ApplicationUser User { get; set; }
}
public class ApplicationClaim : IdentityUserClaim<int>
{
public virtual ApplicationUser User { get; set; }
}
public class ApplicationRole : IdentityRole<int, ApplicationUserRole>
{
public ApplicationRole()
{
}
}
public class ApplicationContext : IdentityDbContext<ApplicationUser, ApplicationRole, int, ApplicationLogin, ApplicationUserRole, ApplicationClaim>
{
//web config connectionStringName DefaultConnection change it if required
public ApplicationContext()
: base("DefaultConnection")
{
Database.SetInitializer<ApplicationContext>(new CreateDatabaseIfNotExists<ApplicationContext>());
}
public static ApplicationContext Create()
{
return new ApplicationContext();
}
protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
base.OnModelCreating(modelBuilder);
modelBuilder.Conventions.Remove<PluralizingTableNameConvention>();
modelBuilder.Conventions.Remove<ManyToManyCascadeDeleteConvention>();
modelBuilder.Conventions.Remove<OneToManyCascadeDeleteConvention>();
}
}
SignInManager에 string userName 대신 TUser 사용자를 받아들이는 다른 공용 메서드가 있으므로 Watson을 업데이트했습니다.승인된 답변은 사용자 이름 서명으로 메서드를 재정의하는 것만 제안합니다.둘 다 재정의해야 합니다. 그렇지 않으면 비활성화된 사용자에게 서명할 수 있습니다.기본 구현의 두 가지 방법은 다음과 같습니다.
public virtual async Task<SignInResult> PasswordSignInAsync(string userName, string password, bool isPersistent, bool lockoutOnFailure)
{
var user = await UserManager.FindByNameAsync(userName);
if (user == null)
{
return SignInResult.Failed;
}
return await PasswordSignInAsync(user, password, isPersistent, lockoutOnFailure);
}
public virtual async Task<SignInResult> PasswordSignInAsync(User user, string password, bool isPersistent, bool lockoutOnFailure)
{
if (user == null)
{
throw new ArgumentNullException(nameof(user));
}
var attempt = await CheckPasswordSignInAsync(user, password, lockoutOnFailure);
return attempt.Succeeded
? await SignInOrTwoFactorAsync(user, isPersistent)
: attempt;
}
CanSignIn을 재정의하는 것은 CheckPasswordSignInAsync에서 호출되는 PreSignInCheck에 의해 호출되기 때문에 저에게 더 나은 해결책인 것 같습니다.소스에서 알 수 있는 바로는 CanSignIn을 재정의하는 것이 모든 시나리오를 포괄해야 합니다.다음은 사용할 수 있는 간단한 구현입니다.
public override async Task<bool> CanSignInAsync(User user)
{
var canSignIn = user.IsEnabled;
if (canSignIn) {
canSignIn = await base.CanSignInAsync(user);
}
return canSignIn;
}
asp.net Core Identity v3에는 사용자의 로그인을 방지하는 새로운 방법이 추가되었습니다.이전에는 계정에 확인된 전자 메일 주소 또는 전화 번호가 있어야 했지만, 이제는 지정할 수 있습니다..RequireConfirmedAccount
의 기본 구현IUserConfirmation<>
서비스는 확인된 전자 메일 주소를 요구하는 것과 동일하게 동작하며, 확인이 의미하는 바를 정의하기 위한 자체 서비스를 제공합니다.
public class User : IdentityUser<string>{
public bool IsEnabled { get; set; }
}
public class UserConfirmation : IUserConfirmation<User>
{
public Task<bool> IsConfirmedAsync(UserManager<User> manager, User user) =>
Task.FromResult(user.IsEnabled);
}
services.AddScoped<IUserConfirmation<User>, UserConfirmation>();
services.AddIdentity<User, IdentityRole>(options => {
options.SignIn.RequireConfirmedAccount = true;
} );
ID를 제거하려면 자체 UserStore를 구현해야 합니다.
또한 이것은 당신에게 도움이 될 것입니다.
언급URL : https://stackoverflow.com/questions/22652118/disable-user-in-aspnet-identity-2-0
'programing' 카테고리의 다른 글
MySQL에서 JSON_EXTRACT를 사용하고 따옴표 없이 문자열을 얻으려면 어떻게 해야 합니까? (0) | 2023.07.31 |
---|---|
Android가 JS 번들을 로드하지 못했습니다. (0) | 2023.07.31 |
ScrollView 내부의 TableView 스크롤이 자연스럽게 동작하도록 하는 방법 (0) | 2023.07.31 |
Android: 태블릿에 세로와 가로를 허용하지만 전화기에 세로를 강제로 설정하시겠습니까? (0) | 2023.07.31 |
Python 인메모리 zip 라이브러리 (0) | 2023.07.31 |