Подход - это звук. Я делал именно это несколько раз.
Вы можете сделать это явным образом в своем коде, так как конструктор BaseMessage по умолчанию защищен.
Вам также необходимо объявить значение дискриминатора для базового класса.
Я предпочитаю строковые значения для дискриминаторов, поскольку они более понятны при выполнении запросов или отчетов SQL. Кроме того, поскольку экземпляры BaseMessage не должны существовать, в in будет использоваться значение null для значения дискриминатора.
<class name="BaseMessage" table="Messages" discriminator-value="null">
<id />
<discriminator column="SourceID" />
<subclass name="NMessage" discriminator-value="NMessage">
</subclass>
<subclass name="BMessage" discriminator-value="BMessage">
</subclass>
<subclass name="CMessage" discriminator-value="CMessage">
</subclass>
</class>
Кроме того, я вижу, что вы сопоставили свойство со столбцом дискриминатора. Вместо этого у вас должен быть метод, который возвращает что-то уникальное для класса - в данном случае код.
Обратите внимание, что вы не можете изменить класс сопоставленной сущности после ее сохранения. Даже не меняя дискриминатор. Если вы изменили его с помощью SQL, ваш кэш 2-го уровня все еще будет содержать версию с исходным классом.
class BaseMessage
{
public virtual string MessageType { return null; }
}
class NMessage : BaseMessage
{
public override string MessageType { return "NMessage"; }
}
Наконец, ваш файл сопоставления слишком многословен, так как содержит значения по умолчанию. Следующие атрибуты и элементы могут быть удалены:
- access = "property" - это значение по умолчанию
- type = "String" - все типы, которые вы используете, могут быть выведены из вашего .NET класса
- column = "COL" - по умолчанию совпадает с именем
- аналогично для элемента столбца id
Все ваши подклассы Message имеют свойство Body, поэтому переместите его в отображение базового класса. Если это поле может быть длиннее, чем ваша база данных varchar, оно должно быть текстовым столбцом и иметь type = "StringCLob", который отображается на строку в .NET
<class name="BaseMessage" table="Messages" discriminator-value="null">
<id name="MessageID">
<generator class="native" />
</id>
<discriminator column="SourceID"/>
<property name="DateCreated" />
<property name="DatePublished" />
<many-to-one name="User" column="UserID" cascade="none" lazy="false" fetch="join" outer-join="true" />
<property name="Body" type="StringCLob" />
<subclass name="NMessage" discriminator-value="NMessage">
</subclass>
<subclass name="BMessage" discriminator-value="BMessage">
<property name="Title" />
</subclass>
<subclass name="CMessage" discriminator-value="CMessage">
<property name="Url" />
</subclass>
</class>