Asp.net mvc ASP.NET MVC 5如何在Identity 2.0中删除用户及其相关数据
我跟随这篇文章删除Identity 2.0中的一个用户 但是,我需要先删除AspNetUserRoles中的所有相关记录,然后删除该用户 我发现了一个用Identity 1.0编写的示例,该示例中使用的一些方法不存在Asp.net mvc ASP.NET MVC 5如何在Identity 2.0中删除用户及其相关数据,asp.net-mvc,asp.net-mvc-5,asp.net-identity,Asp.net Mvc,Asp.net Mvc 5,Asp.net Identity,我跟随这篇文章删除Identity 2.0中的一个用户 但是,我需要先删除AspNetUserRoles中的所有相关记录,然后删除该用户 我发现了一个用Identity 1.0编写的示例,该示例中使用的一些方法不存在 // POST: /Users/Delete/5 [HttpPost, ActionName("Delete")] [ValidateAntiForgeryToken] public async Task&
// POST: /Users/Delete/5
[HttpPost, ActionName("Delete")]
[ValidateAntiForgeryToken]
public async Task<ActionResult> DeleteConfirmed(string id)
{
if (ModelState.IsValid)
{
if (id == null)
{
return new HttpStatusCodeResult(HttpStatusCode.BadRequest);
}
var user = await context.Users.FindAsync(id);
var logins = user.Logins;
foreach (var login in logins)
{
context.UserLogins.Remove(login);
}
var rolesForUser = await IdentityManager.Roles.GetRolesForUserAsync(id, CancellationToken.None);
if (rolesForUser.Count() > 0)
{
foreach (var item in rolesForUser)
{
var result = await IdentityManager.Roles.RemoveUserFromRoleAsync(user.Id, item.Id, CancellationToken.None);
}
}
context.Users.Remove(user);
await context.SaveChangesAsync();
return RedirectToAction("Index");
}
else
{
return View();
}
}
//POST:/Users/Delete/5
[HttpPost,ActionName(“删除”)]
[ValidateAntiForgeryToken]
公共异步任务已确认(字符串id)
{
if(ModelState.IsValid)
{
if(id==null)
{
返回新的HttpStatusCodeResult(HttpStatusCode.BadRequest);
}
var user=wait context.Users.FindAsync(id);
var logins=user.logins;
foreach(登录中的var登录)
{
context.UserLogins.Remove(login);
}
var rolesForUser=await IdentityManager.Roles.GetRolesForUserAsync(id,CancellationToken.None);
if(rolesForUser.Count()>0)
{
foreach(rolesForUser中的var项)
{
var result=await IdentityManager.Roles.RemoveUserFromRoleAsync(user.Id、item.Id、CancellationToken.None);
}
}
context.Users.Remove(用户);
wait context.saveChangesSync();
返回操作(“索引”);
}
其他的
{
返回视图();
}
}
我在任何地方都找不到IdentityManager
,也找不到context。用户也没有FindAsync()
方法
如何在Identity 2.0中正确删除用户及其相关记录?我认为您要查找的类是和。在我看来,他们是更好的方式,而不是直接违背上下文
UserManager定义了一种方法,使您能够从给定角色中删除该用户(由其密钥标识)。它还定义了几种查找方法,如、或。它们都可以用于检索用户。要删除用户,应使用接受用户对象作为参数的方法。要获取用户是Identity成员的角色,您可以使用传递用户ID的方法。我还看到您试图从用户中删除登录名。为此,您应该使用该方法
总之,您的代码看起来与以下代码类似:
// POST: /Users/Delete/5
[HttpPost, ActionName("Delete")]
[ValidateAntiForgeryToken]
public async Task<ActionResult> DeleteConfirmed(string id)
{
if (ModelState.IsValid)
{
if (id == null)
{
return new HttpStatusCodeResult(HttpStatusCode.BadRequest);
}
var user = await _userManager.FindByIdAsync(id);
var logins = user.Logins;
var rolesForUser = await _userManager.GetRolesAsync(id);
using (var transaction = context.Database.BeginTransaction())
{
foreach (var login in logins.ToList())
{
await _userManager.RemoveLoginAsync(login.UserId, new UserLoginInfo(login.LoginProvider, login.ProviderKey));
}
if (rolesForUser.Count() > 0)
{
foreach (var item in rolesForUser.ToList())
{
// item should be the name of the role
var result = await _userManager.RemoveFromRoleAsync(user.Id, item);
}
}
await _userManager.DeleteAsync(user);
transaction.Commit();
}
return RedirectToAction("Index");
}
else
{
return View();
}
}
//POST:/Users/Delete/5
[HttpPost,ActionName(“删除”)]
[ValidateAntiForgeryToken]
公共异步任务已确认(字符串id)
{
if(ModelState.IsValid)
{
if(id==null)
{
返回新的HttpStatusCodeResult(HttpStatusCode.BadRequest);
}
var user=await\u userManager.FindByIdAsync(id);
var logins=user.logins;
var rolesForUser=wait_userManager.GetRolesAsync(id);
使用(var transaction=context.Database.BeginTransaction())
{
foreach(logins.ToList()中的var登录)
{
wait_userManager.removeloginanc(login.UserId,new UserLoginInfo(login.LoginProvider,login.ProviderKey));
}
if(rolesForUser.Count()>0)
{
foreach(rolesForUser.ToList()中的变量项)
{
//项应该是角色的名称
var result=wait_userManager.RemoveFromRoleAsync(user.Id,item);
}
}
wait_userManager.deleteAync(用户);
Commit();
}
返回操作(“索引”);
}
其他的
{
返回视图();
}
}
您需要根据需要调整此代码段,因为我不知道您的IdentityUser实现是什么样子的。记住根据需要声明用户管理器。当您在Visual Studio中使用个人帐户创建新项目时,可以找到一个示例,说明如何做到这一点
如果您使用的是最新版本的ASP.NET,Brad关于在视图中要求@Html.AntiForgeryToken()的观点是不必要的-请参阅
为什么不为AspNetUsers创建一个SQL触发器,这样删除一个用户也会从AspNetUserRoles和AspNetUserLogins中删除用户的相应记录
我需要从许多地方调用DeleteUser,因此我向AccountController添加了一个静态方法(见下文)。我仍在学习MVC,因此我应该感谢大家的评论,特别是1)使用IdentityResult作为返回代码2)以这种方式扩展AccountController的智慧3)将密码(明文)放入模型以验证操作的方法(请参见示例调用)
公共静态异步任务DeleteUserAccount(UserManager用户管理器,
字符串userEmail,ApplicationDbContext上下文)
{
IdentityResult rc=新IdentityResult();
if((userManager!=null)&&&(userEmail!=null)&&&(context!=null))
{
var user=await userManager.findbyemailsync(userEmail);
var logins=user.logins;
var rolesForUser=await userManager.GetRolesAsync(用户);
使用(var transaction=context.Database.BeginTransaction())
{
foreach(logins.ToList()中的var登录)
{
等待userManager.removeloginanc(用户,login.LoginProvider,login.ProviderKey);
}
if(rolesForUser.Count()>0)
{
foreach(rolesForUser.ToList()中的变量项)
{
//项应该是角色的名称
var result=await userManager.RemoveFromRoleAsync(用户,项);
}
}
rc=等待userManager.DeleteAsync(用户);
Commit();
}
}
返回rc;
}
示例调用-表单传递用户的密码
public static async Task<IdentityResult> DeleteUserAccount(UserManager<ApplicationUser> userManager,
string userEmail, ApplicationDbContext context)
{
IdentityResult rc = new IdentityResult();
if ((userManager != null) && (userEmail != null) && (context != null) )
{
var user = await userManager.FindByEmailAsync(userEmail);
var logins = user.Logins;
var rolesForUser = await userManager.GetRolesAsync(user);
using (var transaction = context.Database.BeginTransaction())
{
foreach (var login in logins.ToList())
{
await userManager.RemoveLoginAsync(user, login.LoginProvider, login.ProviderKey);
}
if (rolesForUser.Count() > 0)
{
foreach (var item in rolesForUser.ToList())
{
// item should be the name of the role
var result = await userManager.RemoveFromRoleAsync(user, item);
}
}
rc = await userManager.DeleteAsync(user);
transaction.Commit();
}
}
return rc;
}
// POST: /Manage/DeleteUser
[HttpPost]
[ValidateAntiForgeryToken]
public async Task<IActionResult> DeleteUser(DeleteUserViewModel account)
{
var user = await GetCurrentUserAsync();
if ((user != null) && (user.PasswordHash != null) && (account != null) && (account.Password != null))
{
var hasher = new Microsoft.AspNetCore.Identity.PasswordHasher<ApplicationUser>();
if(hasher.VerifyHashedPassword(user,user.PasswordHash, account.Password) != PasswordVerificationResult.Failed)
{
IdentityResult rc = await AccountController.DeleteUserAccount( _userManager, user.Email, _Dbcontext);
if (rc.Succeeded)
{
await _signInManager.SignOutAsync();
_logger.LogInformation(4, "User logged out.");
return RedirectToAction(nameof(HomeController.Index), "Home");
}
}
}
return View(account);
}
ApplicationDbContext context,
UserManager<ApplicationUser> userManager,
ApplicationUser user
var logins = await userManager.GetLoginsAsync(user);
var rolesForUser = await userManager.GetRolesAsync(user);
using (var transaction = context.Database.BeginTransaction())
{
IdentityResult result = IdentityResult.Success;
foreach (var login in logins)
{
result = await userManager.RemoveLoginAsync(user, login.LoginProvider, login.ProviderKey);
if (result != IdentityResult.Success)
break;
}
if (result == IdentityResult.Success)
{
foreach (var item in rolesForUser)
{
result = await userManager.RemoveFromRoleAsync(user, item);
if (result != IdentityResult.Success)
break;
}
}
if (result == IdentityResult.Success)
{
result = await userManager.DeleteAsync(user);
if (result == IdentityResult.Success)
transaction.Commit(); //only commit if user and all his logins/roles have been deleted
}
}
// GET: Users/Delete/5
public ActionResult Delete(string id)
{
using (SqlConnection sqlCon = new SqlConnection(connectionString))
{
sqlCon.Open();
string query = "DELETE FROM AspNetUsers WHERE Id = @Id";
SqlCommand sqlCmd = new SqlCommand(query, sqlCon);
sqlCmd.Parameters.AddWithValue("@Id", id);
sqlCmd.ExecuteNonQuery();
}
return RedirectToAction("Index");
}
// POST: Users/Delete/5
[HttpPost]
public ActionResult Delete(string id, FormCollection collection)
{
try
{
// TODO: Add delete logic here
return RedirectToAction("Index");
}
catch
{
return View();
}
}