Chr*_*web 6 c# sql-server-2005 entity-framework-4
SQL Server 2005数据库表有一个'createdon'列,其默认值设置为getdate().我正在尝试使用实体框架添加记录.'createdon'列未获得更新.
我是否错过了Entity框架中的任何属性,请提出建议.
Sim*_*ger 12
这是Entity Framework存在问题的少数几个问题之一.假设您有一个类似于以下的类:
public class MyEntity
{
// Id is a PK on the table with Auto-Increment
public int Id { get; set; }
// CreatedOn is a datetime, with a default value
public DateTime CreatedOn { get; set; }
}
Run Code Online (Sandbox Code Playgroud)
现在,您要插入一个新元素:
using(var context = new YourContext())
{
context.MyEntities.Add(new MyEntity())
}
Run Code Online (Sandbox Code Playgroud)
由于EDMX中的定义,实体框架知道如何处理自动增量主键.它不会尝试为Id属性插入值.但是,就实体框架而言,CreatedOn 有一个值:默认值DateTime.因为实体框架不能说"好,它有一个值但我应该忽略它",它会主动插入带有CreatedOn属性值的记录,绕过表上列定义的默认值.
没有简单的方法可以做到这一点.您可以在插入该项时主动将CreatedOn属性设置为DateTime.Now.或者您可以创建一个接口和一个扩展方法对:
public interface ICreatedOn
{
public DateTime CreatedOn { get; set; }
}
public partial class MyEntity : ICreatedOn
{
}
public static TEntity AsNew<TEntity>(this TEntity entity) where TEntity : ICreatedOn
{
if(entity != null)
entity.CreatedOn = DateTime.Now;
return entity;
}
using(var context = new YourContext())
{
context.MyEntities.Add(new MyEntity().AsNew())
}
Run Code Online (Sandbox Code Playgroud)
编辑:为了扩展这一点,这是一个无法解决的问题的原因是因为autoincrement字段背后的含义和具有default值约束的字段.根据定义,自动增量字段应始终由服务器使用种子和所有爵士乐来处理.除非已使用,否则无法为插入上的自动增量字段指定值SET IDENTITY INSERT ON.但是,默认值只是提示"如果我没有指定任何值,请使用此".由于.NET中的值类型不能为null,因此总会有一个值,并且Entity Framework无法推断该字段的默认值(当时)意味着您希望它在SQL Server上默认值.
Pat*_*man 10
在使用设计器和已经显示的一些更漂亮的东西旁边,您还可以通过简单地DatabaseGenerated在字段上设置属性来标记列的计算:
[DatabaseGenerated(DatabaseGeneratedOption.Computed)]
public DateTime CreatedOn { get; set; }
Run Code Online (Sandbox Code Playgroud)
您可以设置StoreGeneratedPattern到Computed(如马尔科姆建议)在实体数据模型的GUI为好.
StoreGeneratedPattern到Computed在属性窗口如下图所示:我已经解决了这个问题,告诉EF该列是"计算的",因此应该单独插入.
如果查看生成的实体的配置
namespace Data.Context
{
// Table
internal partial class MyTableConfiguration : EntityTypeConfiguration<MyTable>
{
public MyTableConfiguration(string schema = "dbo")
{
ToTable(schema + ".MyTable");
HasKey(x => x.Id);
Property(x => x.ColumnName).HasColumnName("ColumnName").IsOptional().HasDatabaseGeneratedOption(DatabaseGeneratedOption.Computed);
....
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
12187 次 |
| 最近记录: |