我使用实体框架使用fluent-api配置设置表:
Property(g => g.DateTime).IsRequired().HasColumnType("datetime2").HasPrecision(0);
表确实成功创建了:
CREATE TABLE [dbo].[Foo] (
[DateTime] DATETIME2 (0) NOT NULL,
);
如您所见,datetime2列的精度已设置为0。因此,我希望检索到的日期时间值根本不包括毫秒,也就是说日期应该看起来像2016年3月13日18:35:37.0000'但是,检索的日期总是包括毫秒。以下是我使用的代码:
var dbcontext = new ApplicationDbContext(); //foo table is empty
dbcontext.Foo.Add(new Entry { DateTime = DateTime.Now });
dbcontext.SaveChanges();
var date = dbcontext.Foo.First().DateTime; //this should be identical to DateTime.Now above except for milliseconds which should be set to zero right?
如果不手动调零毫秒(在插入前或检索后通过C#代码),我怎样才能达到预期的效果?
答案 0 :(得分:1)
如果您只需要没有任何毫秒的日期和时间,请改用smalldatetime
MS SQL类型。它的准确度为1秒。
如果出于某种原因,您希望在数据库中使用datetime2,则无法通过自动方式实现所需的行为。您可以创建一个(计算的)属性MyDateTimeWithoutMs来获取并设置数据库连接属性的正确值。
internal DateTime databaseDateTime { get; set; }
public DateTime MyDateTimeWithoutMs
{
get
{
return databaseDateTime.DateTimeWithoutMs();
}
set
{
databaseDateTime= value.ToDateTimeWithoutMs();
}
}
在模型映射中,为计算属性添加ignore,并将数据库属性映射到实际列名。
public class EntryMap : EntityTypeConfiguration<Entry >
{
public Entry Map()
{
Property(t => t.databaseDateTime)
.HasColumnName("DateTime");
Ignore(t => t.MyDateTimeWithoutMs );
答案 1 :(得分:1)
向@JonSkeet致敬,他告诉我什么是错误的。事实证明,我实例化的第一个dbcontext有某种缓存,这反过来导致提供的日期时间值按原样返回,其毫秒组件完好无损(如图...)。解决此问题的一种方法是,为了获得所需的行为,重新实例化db-context并以tabula-rasa为基础,以确保在datetime上不返回任何缓存的值:
Capacity
或者你可以使用.Entry()。Reload(),它的好处是它不需要实例化一个新的db-context:
var dbcontext = new ApplicationDbContext(); //foo table is empty
dbcontext.Foo.Add(new Entry { DateTime = DateTime.Now });
dbcontext.SaveChanges();
var dbcon2 = new ApplicationDbContext(); //vital
var date = dbcon2.Foo.First().DateTime;
PS:最后但并非最不重要的是,如果您在单元测试项目中使用此代码,请务必在给出它之前重建项目(至少我必须做些什么才能让工作在我的项目)