Как использовать NHibernate для запроса по значениям уникальных ключей

StackOverflow https://stackoverflow.com/questions/1420615

Вопрос

Я хотел бы использовать example.Create() для запроса только уникальных значений экземпляра.Для этого мне нужно узнать значение свойства unique-key, которое было установлено внутри файла сопоставления, например:

  <property name="MyColumn">
    <column name="MyColumn" unique-key="MyUniqueKeyGroup"/>
  </property>

Для лучшего понимания — вот важная часть кода:

criteria.Add(Example.Create(myObject).SetPropertySelector(new MyPropertySelector()));

[...]

public class MyPropertySelector: NHibernate.Criterion.Example.IPropertySelector
{
    #region IPropertySelector Member

    public bool Include(object propertyValue, string propertyName, IType type)
    {
         /*  here is where I want to check if the property belongs 
          *  to the unique-key group 'MyUniqueKeyGroup' and return true if so 
          */
    }

    #endregion
}

Что мне нужно сделать, чтобы узнать, принадлежит ли свойство группе уникальных ключей MyUniqueKeyGroup?

Это было полезно?

Решение

Вам нужно будет исследовать Nhibernate.Cfg.Configuration возражать, чтобы получить это.Вы бы сконструировали это где-нибудь, чтобы создать свой экземпляр ISessionFactory.Что-то вроде этого может сработать:

private NHibernate.Cfg.Configuration _configuration;

[...]

var selector = new MyPropertySelector<MyClass>(_configuration, "MyUniqueKeyGroup");
criteria.Add(Example.Create(myObject)
                    .SetPropertySelector(selector));

[...]

public class MyPropertySelector<T>: NHibernate.Criterion.Example.IPropertySelector
{
    private NHibernate.Cfg.Configuration _onfiguration;
    private IEnumerable<NHibernate.Mapping.Column> _keyColumns;

    public MyPropertySelector(NHibernate.Cfg.Configuration cfg, string keyName)
    {
        _configuration = cfg;
        _keyColumns = _configuration.GetClassMapping(typeof(T))
                                .Table
                                .UniqueKeyIterator
                                .First(key => key.Name == keyName)
                                .ColumnIterator);

    }

    public bool Include(object propertyValue, string propertyName, IType type)
    {
         return _configuration.GetClassMapping(typeof(T))
                          .Properties
                          .First(prop => prop.Name == propertyName)
                          .ColumnIterator
                              .Where(col => !col.IsFormula)
                              .Cast<NHibernate.Mapping.Column>()
                              .Any(col => _keyColumns.Contains(col)))
    }
}

На самом деле я не компилировал это, чтобы проверить, работает ли это, поэтому YMMV.И, конечно же, его можно было бы сделать более эффективным!Он также не выполняет никакого перехвата ошибок (например,если вы дадите ему неправильное имя ключа или несопоставленный тип класса, произойдет сбой).

Ура, Джон

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top