C# 在通用存储库模式中使用ApplicationUser

C# 在通用存储库模式中使用ApplicationUser,c#,generics,asp.net-core,entity-framework-6,C#,Generics,Asp.net Core,Entity Framework 6,是否可以在通用存储库模式中使用asp net core的默认身份验证?如果可以,如何使用 我能够为我的所有代码创建一个使用通用存储库模式的项目,但项目的身份验证端使用默认方式除外 我的存储库看起来像: using System.Linq; using DemoWebsite.Interfaces; using Microsoft.EntityFrameworkCore; namespace DemoWebsite.Data { public class Repository<T>

是否可以在通用存储库模式中使用asp net core的默认身份验证?如果可以,如何使用

我能够为我的所有代码创建一个使用通用存储库模式的项目,但项目的身份验证端使用默认方式除外

我的存储库看起来像:

using System.Linq;
using DemoWebsite.Interfaces;
using Microsoft.EntityFrameworkCore;

namespace DemoWebsite.Data
{
 public class Repository<T> : IRepository<T> where T : class
{
    protected readonly DbContext Context;
    protected DbSet<T> DbSet;

    public Repository(ApplicationDbContext context)
    {
        Context = context;
        DbSet = context.Set<T>();
    }

    public void Add(T entity)
    {
        Context.Set<T>().Add(entity);

        Save();
    }

    public T Get<TKey>(TKey id)
    {
        return DbSet.Find(id);
    }

    public IQueryable<T> GetAll()
    {
        return DbSet;
    }

    public void Update(T entity)
    {
        Save();
    }

    private void Save()
    {
        Context.SaveChanges();
    }
}
}
使用System.Linq;
使用DemoWeb.Interface;
使用Microsoft.EntityFrameworkCore;
名称空间DemoWebsite.Data
{
公共类存储库:IRepository,其中T:class
{
受保护的只读DbContext上下文;
受保护的DbSet-DbSet;
公共存储库(ApplicationDbContext上下文)
{
上下文=上下文;
DbSet=context.Set();
}
公共无效添加(T实体)
{
Context.Set().Add(实体);
Save();
}
公用T Get(TKey id)
{
返回DbSet.Find(id);
}
公共IQueryable GetAll()
{
返回DbSet;
}
公共无效更新(T实体)
{
Save();
}
私有void Save()
{
SaveChanges();
}
}
}
我的ApplicationDbContext类:

public class ApplicationDbContext : IdentityDbContext<ApplicationUser>
{
    public ApplicationDbContext(DbContextOptions<ApplicationDbContext> options)
        : base(options)
    {
    }

    protected override void OnModelCreating(ModelBuilder builder)
    {
        base.OnModelCreating(builder);
        // Customize the ASP.NET Identity model and override the defaults if needed.
        // For example, you can rename the ASP.NET Identity table names and more.
        // Add your customizations after calling base.OnModelCreating(builder);
    }
}
public类ApplicationDbContext:IdentityDbContext
{
公共应用程序DBContext(DbContextOptions选项)
:基本(选项)
{
}
模型创建时受保护的覆盖无效(ModelBuilder)
{
基于模型创建(生成器);
//自定义ASP.NET标识模型,并根据需要覆盖默认值。
//例如,可以重命名ASP.NET标识表名称等。
//在调用base.OnModelCreating(builder)后添加自定义项;
}
}

是的,这是可能的,但要做到这一点需要付出相当大的努力。您必须实现
IUserStore
,并可能实现
IRoleStore
(接口和)

在实现此接口时,还必须实现所有功能接口(用于获取密码、双因素身份验证()、安全戳等)

对于一个示例实现,您可以始终查看的源代码

像这样

public abstract class UserStore<TUser, TRole, TContext, TKey, TUserClaim, TUserRole, TUserLogin, TUserToken, TRoleClaim> :
    IUserLoginStore<TUser>,
    IUserRoleStore<TUser>,
    IUserClaimStore<TUser>,
    IUserPasswordStore<TUser>,
    IUserSecurityStampStore<TUser>,
    IUserEmailStore<TUser>,
    IUserLockoutStore<TUser>,
    IUserPhoneNumberStore<TUser>,
    IQueryableUserStore<TUser>,
    IUserTwoFactorStore<TUser>,
    IUserAuthenticationTokenStore<TUser>
    where TUser : IdentityUser<TKey, TUserClaim, TUserRole, TUserLogin>
    where TRole : IdentityRole<TKey, TUserRole, TRoleClaim>
    where TContext : DbContext
    where TKey : IEquatable<TKey>
    where TUserClaim : IdentityUserClaim<TKey>
    where TUserRole : IdentityUserRole<TKey>
    where TUserLogin : IdentityUserLogin<TKey>
    where TUserToken : IdentityUserToken<TKey>
    where TRoleClaim : IdentityRoleClaim<TKey>
{
    ...
}

然后,
UserManager
和其他标识类将使用您的用户/角色存储。但这比它的价值更麻烦,除非你有一个现有的数据库结构,无法映射到EF/已知的提供者。

是的,这是可能的,但要做到这一点需要付出相当多的努力。您必须实现
IUserStore
,并可能实现
IRoleStore
(接口和)

在实现此接口时,还必须实现所有功能接口(用于获取密码、双因素身份验证()、安全戳等)

对于一个示例实现,您可以始终查看的源代码

像这样

public abstract class UserStore<TUser, TRole, TContext, TKey, TUserClaim, TUserRole, TUserLogin, TUserToken, TRoleClaim> :
    IUserLoginStore<TUser>,
    IUserRoleStore<TUser>,
    IUserClaimStore<TUser>,
    IUserPasswordStore<TUser>,
    IUserSecurityStampStore<TUser>,
    IUserEmailStore<TUser>,
    IUserLockoutStore<TUser>,
    IUserPhoneNumberStore<TUser>,
    IQueryableUserStore<TUser>,
    IUserTwoFactorStore<TUser>,
    IUserAuthenticationTokenStore<TUser>
    where TUser : IdentityUser<TKey, TUserClaim, TUserRole, TUserLogin>
    where TRole : IdentityRole<TKey, TUserRole, TRoleClaim>
    where TContext : DbContext
    where TKey : IEquatable<TKey>
    where TUserClaim : IdentityUserClaim<TKey>
    where TUserRole : IdentityUserRole<TKey>
    where TUserLogin : IdentityUserLogin<TKey>
    where TUserToken : IdentityUserToken<TKey>
    where TRoleClaim : IdentityRoleClaim<TKey>
{
    ...
}

然后,
UserManager
和其他标识类将使用您的用户/角色存储。但这比它的价值更麻烦,除非您有一个无法映射到EF/已知提供商的现有DB结构。

为什么要混合责任?存储库应负责获取保存的数据。验证不是存储库的责任。您应该为此使用类似IAAuthenticationFilter的东西,并将其应用于控制器或操作。当您调用存储库时,用户应该已经获得授权,所以处理身份验证的首选方法是保持原样,只需对我的其余数据使用通用存储库?我只是想把一切都集中起来roof@MarcusS当前位置理论上你可以这样做是的。您需要实现自己的IUserStore及其所有功能(获取密码等,请参见此处的EF Implementation),然后自己注册。更麻烦的是,它是值得的,除非你有一个数据库结构,它不能映射到EF/已知的提供者。为什么混合责任?存储库应负责获取保存的数据。验证不是存储库的责任。您应该为此使用类似IAAuthenticationFilter的东西,并将其应用于控制器或操作。当您调用存储库时,用户应该已经获得授权,所以处理身份验证的首选方法是保持原样,只需对我的其余数据使用通用存储库?我只是想把一切都集中起来roof@MarcusS当前位置理论上你可以这样做是的。您需要实现自己的IUserStore及其所有功能(获取密码等,请参见此处的EF Implementation),然后自己注册。更麻烦的是,除非您有一个无法映射到EF/已知提供者的DB结构,否则它是值得的
userStoreType = typeof(GenericUserStore<,,,>).MakeGenericType(userType, roleType, contextType, keyType);
roleStoreType = typeof(GenericRoleStore<,,>).MakeGenericType(roleType, contextType, keyType);

var services = new ServiceCollection();
services.AddScoped(
    typeof(IUserStore<>).MakeGenericType(userType),
    userStoreType);
services.AddScoped(
    typeof(IRoleStore<>).MakeGenericType(roleType),
    roleStoreType);