2

我有多个实体存储在单个 NHibernate 搜索索引中,希望能够一次查询所有实体。用例是一个返回混合结果的简单搜索页面。因此,例如,代码可能如下所示:

public interface ISearchable {}

[Indexed(Index = "TheIndex")]
public class SearchableEntityA : ISearchable
{
    // Some [Field]s
}

[Indexed(Index = "TheIndex")]
public class SearchableEntityB : ISearchable
{
    // Some other [Field]s
}

这所有索引都很好,当然可以在原始 NHibernate 中查询,如下所示:

session.CreateCriteria<ISearchable>().List<ISearchable>();

我在 ISearchable 上有一些字段,但在 NHibernate 映射中没有专门引用这些字段。

希望我可以说:

var query = "some keyword";
fullTextSession.CreateFullTextQuery<ISearchable>(query).List<ISearchable>();

并检索 ISearchables 列表,其中包含来自各种不同实体的结果。然而,现实是它抛出了NHibernate.HibernateException: Not a mapped entity: NetComposites.Model.ISearchable.

那么,用 NHibernate Search 实现类似于多态查询的最简单方法是什么?

4

1 回答 1

2

exists的重载CreateFullTextQuery,允许您指定要搜索的类型:

fullTextSession.CreateFullTextQuery(query, typeof(EntityA), typeof(EntityB)).List<ISearchable>();

必须指定所有类型有点笨拙,但它们加载得很好。我唯一剩下的问题是我假设你可以默认进行所有字段搜索是不正确的,因此它需要构建MultiFieldQueryParser所有可搜索实体的所有属性:

private static Query ParseQuery(string query, IFullTextSession searchSession)
{
    var parser = new MultiFieldQueryParser(GetAllFieldNames(searchSession), new StandardAnalyzer());
    return parser.Parse(query);
}

private static string[] GetAllFieldNames(IFullTextSession searchSession)
{
    var reader =
        searchSession.SearchFactory.ReaderProvider.OpenReader(
            searchSession.SearchFactory.GetDirectoryProviders(typeof (Company)));
    var fieldNames = reader.GetFieldNames(IndexReader.FieldOption.ALL);
    return fieldNames.Cast<string>().ToArray();
}
于 2012-02-08T13:04:27.803 回答