NHibernate Postgresql DateTime to Time Conversion

半腔热情 提交于 2019-12-09 21:44:49

问题


I'm using Fluent NHibernate to configure my mappings everything works when reading data but when trying to insert or update records that have a Postgresql type of Time I get the error message

"ERROR: 42804: column \"run_time\" is of type time with time zone but expression is of type timestamp without time zone"

It looks like NHibernate might be confused on which DbType to convert the DateTime to as you can see from PostgreSQL and C# Datatypes that there are several DbTypes that DateTime map to.

I also tried specifying a custom type for this column from IUserType but on the NullSafeSet override I get a NullReferenceError

public override void NullSafeSet(IDbCommand cmd, object value, int index)
{
    var obj = (DateTime)value;

    NHibernate.NHibernateUtil.Time.NullSafeSet(cmd, obj, index);
}

Is there some type of hint I can provide to either tell NHibernate to convert the DateTime to a Postgresql "time" type? Or can I achieve this by the IUserType and I'm just doing something wrong?


回答1:


Figured it out!

Apparently the conversion sheet I linked to is either wrong or out of date. It turns out that a System.TimeSpan object is what's needed for Npgsql to do a proper conversion to a Postgresql "time" object. It seems odd to me that they would try to convert something that represents a difference between two time's into what we think of as HH:mm:ss but that's the way it is.

Rather than change the type of my RunTime property from System.DateTime to System.TimeSpan I've instead created a custom IUserType and have overriden NullSafeSet to look like

public override void NullSafeSet(IDbCommand cmd, object value, int index)
{
    var obj = (DateTime)value;

    ((IDbDataParameter) cmd.Parameters[index]).Value = new TimeSpan(0, obj.Hour, obj.Minute, obj.Second);
}



回答2:


You might be able to fix this issue by defining your mapping like this:

Map(x => x.RunTime, "run_time").CustomSqlType("time");



回答3:


If you think NH has invalid definitions for data types, you can report them here: https://nhibernate.jira.com/browse/NH + in the mean time you can drive your own dialect to solve that. something like:

public class CustomDialect : OriginalDialect
{
    public CustomDialect()
    {
      //... add your new definitions here to override default values    
    }
}

now you can use it this way:

var dbType = XyzConfiguration.Standard
                       ...
                       .Dialect<CustomDialect>();


来源:https://stackoverflow.com/questions/6129558/nhibernate-postgresql-datetime-to-time-conversion

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!