繁体   English   中英

AddOrUpdate的通用包装方法失败

[英]Generic wrapper method for AddOrUpdate fails

我正在尝试为EF迁移AddOrUpdate方法编写通用包装程序/扩展方法,但是,在设计期间我收到以下错误消息:

在此处输入图片说明

这是我的代码:

public static void InsertOrUpdate(this Object item, Func<Object, Object> PrimaryKeyMember, DbContext Db, Func<DbContext, DbSet> DbSetAttribute, bool Commit = false)
{
    try
    {
        DbSetAttribute.Invoke(Db).AddOrUpdate(PrimaryKeyMember, item);

        //Commit if required
        if (Commit)
            Db.SaveChanges();

    }
    catch (Exception e)
    {
        Trace.TraceError(e.ToString());
        throw;
    }

}

我仍然对泛型还不陌生,但是我可以推断出,这与AddOrUpdate方法需要“引用类型”这一事实有关。 我也尝试了以下方法:

public static void InsertOrUpdate<T>(this Object item, Func<Object, Object> PrimaryKeyMember, DbContext Db, Func<DbContext, DbSet<T>> DbSetAttribute, bool Commit = false)
{
    try
    {
        DbSetAttribute.Invoke(Db).AddOrUpdate<T>(PrimaryKeyMember, item);

        //Commit if required
        if (Commit)
            Db.SaveChanges();

    }
    catch (Exception e)
    {
        Trace.TraceError(e.ToString());
        throw;
    }

}

但是,这会在设计时导致以下错误:

为了在通用类型或方法blablabla.AddOrUpdate(...)中将其用作参数TEntity,类型“ T”必须为引用类型。

我想念什么? 我不确定“引用类型”是什么...

最终的工作代码

我现在正在使用以下代码,该代码利用了AddOrUpdate的替代之一:

public static void InsertOrUpdate<T>(this T item, Expression<Func<T, object>> IdentifierExpression, DbContext Db, Func<DbContext, IDbSet<T>> DbSetAttribute, bool Commit = false) where T: class
{
    try
    {
        DbSetAttribute.Invoke(Db).AddOrUpdate(IdentifierExpression, item);

        //Commit if required
        if (Commit)
            Db.SaveChanges();

    }
    catch (Exception e)
    {
        Trace.TraceError(e.ToString());
        throw;
    }
}

如果您尝试包装此DbSetMigrationsExtensions.AddOrUpdate扩展,则我无法理解Func<Object, Object> PrimaryKeyMember含义。

无论如何, AddOrUpdate被限制为使用类(==引用类型)作为实体类型。 因此,您的包装方法也必须以这种方式进行约束:

public static void InsertOrUpdate<T>(this Object item, Func<Object, Object> PrimaryKeyMember, DbContext Db, Func<DbContext, DbSet<T>> DbSetAttribute, bool Commit = false)
    where T : class
{
     // ...
}

UPD

由于您尝试使用AddOrUpdate 重载, AddOrUpdate应注意, Func<...>Expression<Func<...>>是两种不同的类型。 第一个是委托,而第二个是树的代码表示形式,可以将其编译为具有特定签名的委托。

您必须将PrimaryKeyMember参数类型从Func<T, object>更改为Expression<Func<T, object>>

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

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