简体   繁体   中英

How to pass a generic type object to a class constructor

I have a generic class that will play the repository role, and I have a second class, this second class should receive an object from the generic repository in the constructor.

Generic class (Repository):

public sealed class Repo<TContext> : IRepo<TContext>, IDisposable where TContext : DbContext, IDbContextFactory<TContext>, new()
{
    #region properties

    /// <summary>
    /// Private DBContext property
    /// </summary>
    private DbContext _Context { get; } = null;

    /// <summary>
    /// Determine if Lazy Loading either activate or not
    /// </summary>
    private bool _LazyLoaded { get; set; }

    #endregion

    #region Construcors

    public Repo(bool LazyLoaded)
    {
        _Context                                  = new TContext();
        _LazyLoaded                               = LazyLoaded;
        _Context.ChangeTracker.LazyLoadingEnabled = LazyLoaded;
    }

    public Repo(DbContext context,bool LazyLoaded)
    {
        _Context                                  = context;
        _LazyLoaded                               = LazyLoaded;
        _Context.ChangeTracker.LazyLoadingEnabled = LazyLoaded;
    }

    public Repo(IConfiguration configuration, string connectionString,bool LazyLoaded)
    {
        _Context                                  = new TContext().GetInstance(configuration, connectionString);
        _LazyLoaded                               = LazyLoaded;
        _Context.ChangeTracker.LazyLoadingEnabled = LazyLoaded;
    }

    #endregion
}

What I tried in my second class:

class UOW:IUOW
{
    public UOW(Repo<DbContext> repo)
    {
        
    }

    public void Commit()
    {

    }

    public void RollBack()
    {

    }
}

But I got these two errors:

CS0311 The type 'Microsoft.EntityFrameworkCore.DbContext' cannot be used as type parameter 'TContext' in the generic type or method 'Repo'. There is no implicit reference conversion from 'Microsoft.EntityFrameworkCore.DbContext' to 'Microsoft.EntityFrameworkCore.IDbContextFactory<Microsoft.EntityFrameworkCore.DbContext>'.

CS0310 'DbContext' must be a non-abstract type with a public parameterless constructor in order to use it as parameter 'TContext' in the generic type or method 'Repo'

截屏

How I can configure the constructor of my second class to receive an object from the repo generic class?

There are multiple issues with your code, but to take the error you are concerned with here, DbContext is not a non-abstract type so you cannot use it with the new() generic constraint. It also does not implement IDbContextFactory . There's a couple of things you can do. First would be to make UOW generic and match the same generic constraints, like this:

class UOW<TContext> : IUOW
    where TContext : DbContext, IDbContextFactory<TContext>, new()
{
    public UOW(Repo<TContext> repo)
    {
    }
}

The second is to use a concrete class that does work with all of those constraints, for example:

class MyContext : DbContext, IDbContextFactory<MyContext>
{
    public MyContext CreateDbContext()
    {
        throw new NotImplementedException();
    }
}

class UOW : IUOW
{
    public UOW(Repo<MyContext> repo)
                 // ^^^^^^^^^ Use the new object here
    {
    }
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM