我正在使用winforms编写CRUD,通过Linq2Sql连接到MS SqlServer 2008 当我的应用程序的用户想要删除数据库中的记录时,我不希望它被物理删除。我只想将一个名为“DlDat”的列设置为当前日期时间,然后更新记录而不是删除它。为了在Linq中强制执行此行为,我扩展了由sqlmetal自动生成的Delete(表)方法 如果是我有一个名为“Unit”的数据库表和一个名为“PdpDataContext”的datacontext,代码如下所示:
public partial class PdpDataContext
{
public PdpDataContext() : base()
{
OnCreated();
}
partial void DeleteUnit(Unit instance)
{
instance.DLDAT = DateTime.Now;
this.ExecuteDynamicUpdate(instance);
}
partial void UpdateUnit(Unit instance)
{
instance.CHDAT = DateTime.Now;
this.ExecuteDynamicUpdate(instance);
}
}
但是当我做删除时:
PdpDataContext cx = new PdpDataContext();
cx.ObjectTrackingEnabled = true;
Unit u = new Unit();
u = cx.Unit.Single(x => x.INTUNITNO == 1);
cx.Unit.DeleteOnSubmit(u);
cx.SubmitChanges();
我收到一个SqlException“WHERE附近的错误语法”。记录上下文的SQL输出我看到Linq尝试进行“空”更新:
UPDATE [dbo].[Unit]
SET
WHERE ([INTUNITNO] = @p0) AND ([version] = @p1)
这可能是因为当上下文的ChangeSet只包含“删除”而没有“更新”时,我使用ExecuteDynamicUpdate。
我可以解决这个问题,只需更新记录,而不是在用户按下删除按钮或使用存储过程时删除它。但由于我是Linq世界的新手,我想知道是否有另一种方法可以使用datacontext。
答案 0 :(得分:1)
我想知道在表上使用“INSTEAD OF”触发器(删除)是不是更好......或者只是不要骗LINQ:如果你想做一个UPDATE(不是DELETE) ,然后更新对象(不要删除它)。例如,在模拟删除的数据上下文中编写方法,而不是使用DeleteOnSubmit
。
您也可以通过覆盖SubmitChanges并调查增量来做一些事情,但我不确定这是一个好主意
答案 1 :(得分:1)
这样做的问题是,linq假设您将使用与您重写的相同的CRUD操作。看一下这篇文章(Responsibilities of the Developer In Overriding Default Behavior (LINQ to SQL))
这就是我要做的事情:
partial void DeleteUnit(Unit instance)
{
//instance.DLDAT = DateTime.Now;
//this.ExecuteDynamicUpdate(instance);
PdpDataContext cx = new PdpDataContext();
cx.ObjectTrackingEnabled = true;
Unit u = new Unit();
u = cx.Unit.Single(x => x.INTUNITNO == 1);
u.DLDAT = DateTime.Now;
cx.SubmitChanges();
}