AddApiAuthorization 无隐式引用转换 ASP Core 3.0

AddApiAuthorization no implicit reference conversion ASP Core 3.0

尝试在 ASP.NET Core 3.1 中实现 Identity。在解决这个问题时遇到了一些问题。

这是我的设置

  1. 我有单独的项目

    • 门户网站
    • Portal.ApplicationCore
    • Portal.Infrastructure
    • Portal.Domain
  2. 在Portal.Domain我继承了Identity模型

     public class AppRole : IdentityRole<int>
     {
           [Required]
           public int OrganizationID { get; set; }
    
           [Required(ErrorMessage = "Display name is Required.")]
           [MaxLength(100, ErrorMessage = "Please enter Display name less than 100 characters.")]
           public string DisplayName { get; set; }
    
           [ForeignKey("OrganizationID")]
           public Organization Organization { get; set; }
      }
    
      public class AppUser : IdentityUser<int>
      {
           [Required]
           public int OrganizationID { get; set; }
    
           [ForeignKey("OrganizationID")]
           public Organization Organization { get; set; }
      }
    
  3. 在Portal.Infrastructure中我实现了DBContext

      public class ApplicationDbContext : IdentityDbContext<AppUser, AppRole, int>
      {
             private IDbContextTransaction _transaction;
             public ApplicationDbContext(DbContextOptions<ApplicationDbContext> options)
              : base(options)
             {
             }
    
             public DbSet<Organization> Organizations { get; set; }
    
    
        }
    

终于在我的Startup.cs弹出错误-

Severity Code Description Project File Line Suppression State Error CS0311 The type 'Portal.Infrastructure.DAL.DatabaseContext.ApplicationDbContext' cannot be used as type parameter 'TContext' in the generic type or method 'IdentityServerBuilderConfigurationExtensions.AddApiAuthorization(IIdentityServerBuilder)'. There is no implicit reference conversion from 'Portal.Infrastructure.DAL.DatabaseContext.ApplicationDbContext' to 'IdentityServer4.EntityFramework.Interfaces.IPersistedGrantDbContext'.

谁能帮帮我?

终于解决了我的问题。我将 post 放在这里,它可能对某些人有所帮助。

  1. 我创建自定义 ApiAuthorizationDbContext

    /// <summary>
    /// Database abstraction for a combined <see cref="DbContext"/> using ASP.NET 
    ///Identity and Identity Server.
    /// </summary>
    /// <typeparam name="TUser"></typeparam>
    /// <typeparam name="TRole"></typeparam>
    /// <typeparam name="TKey">Key of the IdentityUser entity</typeparam>
    public class KeyApiAuthorizationDbContext<TUser, TRole, TKey> : 
    IdentityDbContext<TUser, TRole, TKey>, IPersistedGrantDbContext
    where TUser : IdentityUser<TKey>
    where TRole : IdentityRole<TKey>
    where TKey : IEquatable<TKey>
    {
        private readonly IOptions<OperationalStoreOptions> _operationalStoreOptions;
    
        /// <summary>
        /// Initializes a new instance of <see cref="ApiAuthorizationDbContext{TUser, 
        ///TRole, TKey}"/>.
        /// </summary>
        /// <param name="options">The <see cref="DbContextOptions"/>.</param>
        /// <param name="operationalStoreOptions">The <see 
        ///cref="IOptions{OperationalStoreOptions}"/>.</param>
        public KeyApiAuthorizationDbContext(
        DbContextOptions options,
        IOptions<OperationalStoreOptions> operationalStoreOptions)
        : base(options)
        {
            _operationalStoreOptions = operationalStoreOptions;
        }
    
        /// <summary>
        /// Gets or sets the <see cref="DbSet{PersistedGrant}"/>.
        /// </summary>
        public DbSet<PersistedGrant> PersistedGrants { get; set; }
    
        /// <summary>
        /// Gets or sets the <see cref="DbSet{DeviceFlowCodes}"/>.
        /// </summary>
        public DbSet<DeviceFlowCodes> DeviceFlowCodes { get; set; }
    
        Task<int> IPersistedGrantDbContext.SaveChangesAsync() => 
                base.SaveChangesAsync();
    
        /// <inheritdoc />
        protected override void OnModelCreating(ModelBuilder builder)
        {
            base.OnModelCreating(builder);
            builder.ConfigurePersistedGrantContext(_operationalStoreOptions.Value);
        }
    }
    
    /// <summary>
    /// Database abstraction for a combined <see cref="DbContext"/> using ASP.NET 
    ///Identity and Identity Server.
    /// </summary>
    /// <typeparam name="TUser"></typeparam>
    public class ApiAuthorizationDbContext<TUser> : 
    KeyApiAuthorizationDbContext<TUser, IdentityRole, string>
    where TUser : IdentityUser
    {
        /// <summary>
        /// Initializes a new instance of <see 
        ///cref="ApiAuthorizationDbContext{TUser}"/>.
        /// </summary>
        /// <param name="options">The <see cref="DbContextOptions"/>.</param>
        /// <param name="operationalStoreOptions">The <see 
        ///cref="IOptions{OperationalStoreOptions}"/>.</param>
        public ApiAuthorizationDbContext(
        DbContextOptions options,
        IOptions<OperationalStoreOptions> operationalStoreOptions)
        : base(options, operationalStoreOptions)
        {
        }
    }
    
  2. 更改 DbContext

    public class ApplicationDbContext : KeyApiAuthorizationDbContext<AppUser, AppRole, 
    int>
    {
        public ApplicationDbContext(
            DbContextOptions options,
            IOptions<OperationalStoreOptions> operationalStoreOptions) : base(options, 
            operationalStoreOptions)
        {
        }
        public DbSet<Organization> Organizations { get; set; }
    }
    
  3. 最后,改startup.cs

    services.AddIdentityServer()                
        .AddApiAuthorization<AppUser, ApplicationDbContext>();