NHibernate вставляя NULL вместо фактического значения - PullRequest
0 голосов
/ 16 октября 2019

Я создаю новый объект сущности:

var obj = new MyEntity()
{
    MyProperty = ""
};

MyProperty имеет not-null="true", установленный в файле отображения MyEntity.hbm.xml.

Затем я сохраняю его с помощью ISession установлен на FlushMode.Commit:

session.Persist(obj);

Persist принимает это, потому что MyProperty не ноль, а пустая строка. Фиксация сейчас невозможна, поскольку пустая строка в базе данных Oracle совпадает с NULL. Если для MyProperty установлено значение null, метод Persist выдает исключение, но не для пустой строки.

Затем я изменяю значение MyProperty:

obj.MyProperty = "something";

... и зафиксировать:

using(ITransaction tx = session.BeginTransaction()) {
    tx.Commit(); // throws exception, read below
}

Исключение:

NHibernate.Exceptions.GenericADOException: не удалось вставить: [MyEntity] [SQL: ВСТАВИТЬ В MYENTITY (MYPROPERTY,MYENTITYID) VALUES (?,?)]

=> InnerException: Oracle.DataAccess.Client.OracleException: ORA-01400: невозможно вставить NULL в ("MYENTITY". "MYPROPERTY")

Я ожидаю, что Nhibernate вставит "something" вместо пустой строки. Что здесь происходит? Почему не вставляется "something"?


Полный пример:

using(var session = sessionFactory.OpenSession()) {
    session.FlushMode = FlushMode.Commit;

    var obj = new MyEntity
    {
        MyProperty = ""
    };
    session.Persist(obj);
    obj.MyProperty = "something";
    using(ITransaction tx = session.BeginTransaction()) {
        tx.Commit(); // throws the exception
    }
}

MyEntity класс:

Public Class MyEntity
    Implements INotifyPropertyChanged

    Public Overridable Property MyEntityID As Integer
    Public Overridable Property MyProperty As String

    Public Event PropertyChanged As PropertyChangedEventHandler Implements INotifyPropertyChanged.PropertyChanged

    Public Overrides Function Equals(obj As Object) As Boolean
        If (ReferenceEquals(Me, obj)) Then
            Return True
        End If
        Dim TestEntity As MyEntity = TryCast(obj, MyEntity)
        If (TestEntity Is Nothing) Then
            Return False
        End If
        Return GetHashCode.Equals(TestEntity.GetHashCode)
    End Function

    Public Overrides Function GetHashCode() As Integer
        Return MyEntityID Xor MyProperty.GetHashCode
    End Function
End Class

Отображение MyEntity.hbm.xmlфайл:

<hibernate-mapping xmlns="urn:nhibernate-mapping-2.2" assembly="My.Assembly" namespace="My.Namespace">
    <class name="MyEntity" table="MYENTITY">
        <id name="MyEntityID" column="MYENTITYID"><generator class="native"><param name="sequence">MY_SEQUENCE</param></generator></id>
        <property name="MyProperty" column="MYPROPERTY" not-null="true" />
    </class>
</hibernate-mapping>
...