简体   繁体   English

Fluent NHibernate / SQL 服务器中的时间戳版本

[英]Version as timestamp in Fluent NHibernate / SQL Server

Using FNH w/ SQL Server 2008, I'm trying to add a Version as a timestamp, but running into the SQLDateTime Overflow error because the value is passed as 1/1/0001 12:00:00 AM.使用带有 SQL Server 2008 的 FNH,我尝试将版本添加为时间戳,但由于该值作为 1/1/0001 12:00:00 AM 传递,因此遇到了 SQLDateTime 溢出错误。 I found this (also referenced here ), but still experiencing the problem.我找到了这个(也在这里引用),但仍然遇到问题。

// entity base
public abstract class EntityBase
{
    public virtual Int64 Id { get; set; }
    public virtual DateTime Version { get; set; }
}

// entity base map
public abstract class EntityBaseMap<T> : ClassMap<T> where T : EntityBase
{
    public EntityBaseMap()
    {
        Id(x => x.Id).GeneratedBy.Identity();
        OptimisticLock.Version();
        Version(x => x.Version)
           .CustomType("Timestamp");

    }
}    

The SQL Server data type is "datetime". SQL 服务器数据类型为“日期时间”。

I'm guessing its something small and stupid, but haven't found the cause yet - what am I missing?我猜它的一些小而愚蠢的东西,但还没有找到原因 - 我错过了什么?

EDIT: Action method for the actual "save" code编辑:实际“保存”代码的操作方法

    public ActionResult Create()
    {
        int currMaxSortOrder = session.CreateCriteria(typeof(Section))
                            .SetProjection(Projections.ProjectionList().Add(Projections.Max("Sortorder")))
                            .UniqueResult<int>();
        SectionViewModel sectionViewModel = new SectionViewModel();
        sectionViewModel.Sortorder = currMaxSortOrder + 1;
        return View("Create", "_AdminLayout", sectionViewModel);
    }

    [HttpPost]
    public ActionResult Create(SectionViewModel sectionInputModel)
    {
        if (ModelState.IsValid)
        {
            section = new Section();
            Mapper.Map(sectionInputModel, section);
            using (var tx = session.BeginTransaction())
            {
                session.SaveOrUpdate(section);
        tx.Commit();
            }
            return RedirectToAction("index", "pages").WithFlash(new { success = "Section '" + section.Name + "' was successfully added." });
        }
        return View("Create", "_AdminLayout", section);
    }

Edit 2: Added section entity & mapping编辑 2:添加了部分实体和映射

    public class Section : EntityBase
    {
        public virtual String Name { get; set; }
        public virtual int Sortorder { get; set; }
        public virtual String RedirectUrl { get; set; }
        public virtual IList<Page> Pages { get; set; }

        public Section()
        {
            Pages = new List<Page>();
        }

        public virtual void AddPage(Page page)
        {
            page.Section = this;
            this.Pages.Add(page);
        }
    }

    public class SectionMap : EntityBaseMap<Section>
    {
        public SectionMap()
        {
            Map(x => x.Name);
            Map(x => x.Sortorder);
            Map(x => x.RedirectUrl);
            // one to many relationship
            HasMany(x => x.Pages)
                .Inverse()
                .Cascade.All();
        }
    }
}

sheepish Doh!害羞的Doh! moment片刻

(Adding this in case any other n00bs like me run into the same problem) (添加这个以防像我这样的任何其他n00bs遇到同样的问题)

I finally dug deeper and realized that I had configured it to use AutoMapping while I was creating maps that would only work with FluentMapping.我终于深入挖掘并意识到我已经将它配置为使用 AutoMapping,而我正在创建只能使用 FluentMapping 的地图。 Reverted to use FluentMapping and the Version started working perfectly!恢复使用 FluentMapping,版本开始完美运行!

I'm guessing I could possibly use AutoMapping and add a convention that will treat a column named "Version" with CustomType("Timestamp"), but for now am going to use FluentMapping until I get more up to speed.我猜我可能会使用 AutoMapping 并添加一个约定,该约定将使用 CustomType(“Timestamp”)处理名为“Version”的列,但现在我将使用 FluentMapping,直到我加快速度。

This might be the classic .NET min datetime.= SQL Server min datetime.这可能是经典的 .NET min datetime.= SQL Server min datetime。

The min datetime in .NET is in the year 0001, but in SQL server the min date can only go as low as the year 1753. You're getting an overflow in SQL Server because the SQL datetime type can't store the date you're trying to pass. The min datetime in .NET is in the year 0001, but in SQL server the min date can only go as low as the year 1753. You're getting an overflow in SQL Server because the SQL datetime type can't store the date you'重新尝试通过。

You might have better luck with the datetime2 type, but I'm not sure of the compatibility with Hibernate.您可能对 datetime2 类型有更好的运气,但我不确定与 Hibernate 的兼容性。

See this article for more info: http://blog.malevy.net/2010/01/datetimeminvalue-sql-server-minimum.html有关更多信息,请参阅本文: http://blog.malevy.net/2010/01/datetimeminvalue-sql-server-minimum.html

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

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