nHibernate Euro symbol € change for character ¿

蹲街弑〆低调 提交于 2021-01-28 08:22:37

问题


I've tried save a Euro Symbol using NHibernate and FluentNHibernate in a database Oracle 11g.

I have checked a log from NHibernate and see the generated sql statement:

UPDATE CURRENCY
SET    DESCRIPTION = 'Euro',
       SYMBOL = '€',
WHERE  ID = 63

When the query from table CURRENCY execute, the column SYMBOL returns ¿

I've tried change the FluentNHibernate Mapping for the column SYMBOL using AnsiString, like this:

Map((x) => x.Symbol).Column("SYMBOL").CustomType("AnsiString").Not.Nullable();

But it doesn't work.

I tried too change type of column for NVARCHAR2 and change FluentNHibernate Mapping for:

Map((x) => x.Symbol).Column("SYMBOL").CustomSqlType("NVARCHAR2").Not.Nullable();

But it doesn't work too.

How can I get it working?


回答1:


You could use NVARCHAR2 for all strings in your app if they are all NVARCHAR2 in the DB (otherwise you might get performance problems because of conversions to VARCHAR2) - but you need at least NHibernate 5.0 for it. Set this prop in NHibernate config to true: oracle.use_n_prefixed_types_for_unicode

nHibernateConfig.SetProperty("oracle.use_n_prefixed_types_for_unicode", "true");

A better solution, if you have mixed VARCHAR2 and NVARCHAR2 columns, is to use a custom type for NVARCHAR2 columns/properties:

public class UnicodeStringType : IUserType
{
    public 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 NullSafeGet(IDataReader rs, string[] names, object owner)
    {
        var value = NHibernateUtil.String.NullSafeGet(rs, names[0]) as string;
        return value;
    }

    public void NullSafeSet(IDbCommand cmd, object value, int index)
    {
        var parameter = (IDataParameter)cmd.Parameters[index];
        ((OracleParameter)parameter).OracleDbType = OracleDbType.NVarchar2;
        parameter.Value = value;
    }

    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 SqlType[] SqlTypes => new[] { new SqlType(DbType.String) };
    public Type ReturnedType => typeof(string);
    public bool IsMutable => false;
}

You use it like this in mappings:

Map((x) => x.Symbol).Column("SYMBOL").CustomType<UnicodeStringType>().Not.Nullable();


来源:https://stackoverflow.com/questions/47697905/nhibernate-euro-symbol-%e2%82%ac-change-for-character

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