NHibernate сопоставления самостоятельно присоединился к таблице? - PullRequest
0 голосов
/ 18 июня 2011

Это может быть очень просто, но я думаю, что что-то упустил.У меня есть самостоятельная таблица Units, у каждого юнита есть основной блок:

enter image description here

Чтобы я мог запросить что-то вроде этого:

enter image description here

Таблица units сопоставлена ​​со следующим классом:

public class Units
{
    public virtual int Unit_Id { get; private set; }
    public virtual string Unit { get; set; }
    public virtual decimal Unit_Value { get; set; } 
    public virtual Units Main_Unit { get; set; }
}

С файлом сопоставления .hbm следующим образом:

<?xml version="1.0" encoding="utf-8" ?>
<hibernate-mapping xmlns="urn:nhibernate-mapping-2.2" assembly="NewA.Domain"     namespace="NewA.Domain">
   <class name="NewA.Domain.Entities.Units,NewA.Domain" table="Units">
    <id name="Unit_Id" column="Unit_Id" type="Int32" length="4" unsaved-value="0"> 
      <generator class="native">
      </generator>
    </id>
    <property name="Unit" column="Unit" type="string" length="50" not-null="true"/>
    <one-to-one name="Main_Unit" class="NewA.Domain.Entities.Units,NewA.Domain"/>
  </class>
</hibernate-mapping>

При тестировании этих объектов сследующий код:

Units unit = _UnitsRepository.GetById(2);
string parent_unitname = unit.Main_Unit.Unit;
Assert.AreEqual("pack",parent_unitname);

Я получил следующее исключение:

Expected values to be equal.

Expected Value : "pack"
Actual Value   : "kg"

Проблема в том, что свойство Main_Unit сущности Unitссылки на себя, так чего мне здесь не хватает ?? и как я могу написать что-то вроде рекурсивного SQL CTE для применения рангов и т. д., потому что у меня такая же проблема с другими более сложными самосоединяющимися таблицами с более сложными запросами.

1 Ответ

3 голосов
/ 18 июня 2011

Вам нужно сопоставление «многие к одному», а не «один к одному». Попробуйте эту конфигурацию:

<hibernate-mapping xmlns="urn:nhibernate-mapping-2.2">
  <class xmlns="urn:nhibernate-mapping-2.2" name="NewA.Domain.Entities.Units.Units, NewA.Domain, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null" table="`Units`">
    <id name="Unit_Id" type="System.Int32, mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089">
      <column name="Unit_Id" />
      <generator class="native" />
    </id>
    <property name="Unit" type="System.String, mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089">
      <column name="Unit" />
    </property>
    <property name="Unit_Value" type="System.Decimal, mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089">
      <column name="Unit_Value" />
    </property>
    <many-to-one class="NewA.Domain.Entities.Units.Units, NewA.Domain, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null" name="Main_Unit">
      <column name="Main_Unit_id" />
    </many-to-one>
  </class>
</hibernate-mapping>

Я предлагаю вам попробовать Свободный NHibernate - он может динамически генерировать сопоставления для вас. Вот конфигурация, которую я использовал:

var fluent = Fluently.Configure()
    .Mappings(c => c.AutoMappings.Add(AutoMap.AssemblyOf<Units>()
        .Override<Units>(u => u.Id(uu => uu.Unit_Id).GeneratedBy.Native())))
    .Database(() => SQLiteConfiguration.Standard.UsingFile("test.sqlite3"));

var configuration = fluent.BuildConfiguration();

// Generate database schema
new SchemaExport(configuration).Create(false, true);

var sessionFactory = configuration.BuildSessionFactory();
// Now just open session and do whatever you need
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...