我最终使用 IUserType 实现了一个新的用户类型。事实上,我发现了一种新颖的方法,可以最大限度地减少为不可变类型实现新用户类型所需的工作,因为在扩展不可变类型(如 DateTime)时,只有少数成员需要真正实现。这是我的代码:
[Serializable]
public class DateTimeKindLocalType : BaseImmutableUserType<DateTime>
{
public override object NullSafeGet(IDataReader rs, string[] names, object owner)
{
//This is the line that I needed
return DateTime.SpecifyKind((DateTime)NHibernateUtil.DateTime2.NullSafeGet(rs, names), DateTimeKind.Local);
}
public override void NullSafeSet(IDbCommand cmd, object value, int index)
{
NHibernateUtil.DateTime2.NullSafeSet(cmd, value, index);
}
public override SqlType[] SqlTypes
{
get { return new[] {NHibernateUtil.DateTime2.SqlType}; }
}
}
[Serializable]
public class DateTimeKindLocalTypeConvention
: UserTypeConvention<DateTimeKindLocalType>
{
}
[Serializable]
public class DateTimeKindLocalNullableType : BaseImmutableUserType<DateTime?>
{
public override object NullSafeGet(IDataReader rs, string[] names, object owner)
{
if (owner == null)
return null;
return DateTime.SpecifyKind((DateTime)NHibernateUtil.DateTime2.NullSafeGet(rs, names), DateTimeKind.Local);
}
public override void NullSafeSet(IDbCommand cmd, object value, int index)
{
NHibernateUtil.DateTime2.NullSafeSet(cmd, value, index);
}
public override SqlType[] SqlTypes
{
get { return new[] { NHibernateUtil.DateTime2.SqlType }; }
}
}
[Serializable]
public class DateTimeKindLocalNullableTypeConvention
: UserTypeConvention<DateTimeKindLocalNullableType>
{
}
[Serializable]
public abstract class BaseImmutableUserType<T> : IUserType
{
public abstract object NullSafeGet(IDataReader rs, string[] names, object owner);
public abstract void NullSafeSet(IDbCommand cmd, object value, int index);
public abstract SqlType[] SqlTypes { get; }
public new bool Equals(object x, object y)
{
if (ReferenceEquals(x, y))
{
return true;
}
if (x == null || y == null)
{
return false;
}
return x.Equals(y);
}
public int GetHashCode(object x)
{
return x.GetHashCode();
}
public object DeepCopy(object value)
{
return value;
}
public object Replace(object original, object target, object owner)
{
return original;
}
public object Assemble(object cached, object owner)
{
return DeepCopy(cached);
}
public object Disassemble(object value)
{
return DeepCopy(value);
}
public Type ReturnedType
{
get { return typeof(T); }
}
public bool IsMutable
{
get { return false; }
}
}
基本上,我已经创建(从其他地方复制,抱歉忘记了源代码)一个名为的基类BaseImmutableUserType<T>
,它基本上IUserType
基于不可变类型创建一个,但允许子类扩展NullSafeGet()
andNullSafeSet()
操作的功能(本质上是 Get 和 Set 操作和连同 SqlTypes,这就是我需要在子类中覆盖的所有内容)。我想从长远来看,我需要更多地覆盖不同的类型,所以我决定对不可变类型使用通用解决方案。另一点需要注意的是,我必须同时DateTime
执行DateTime?
. 这是我的流利配置:
_fnhConfig = Fluently.Configure().Database(
MsSqlConfiguration.MsSql2008.ConnectionString(ConnectionString)
).Mappings(m => m.FluentMappings.AddFromAssemblyOf<DataAccess.NHMG.Fluent.Mapping.DBBufferMap>()
.Conventions.Add(
DefaultLazy.Never()
,DefaultCascade.None()
===> ,new DateTimeKindLocalTypeConvention()
===> ,new DateTimeKindLocalNullableTypeConvention()
));
如果有问题请告诉我,我会尽快回答。