2

我正在尝试包含一个相关文档(特别是 Sitecore,Lucene 文档是 an Item),以便当 Lucene 索引为 A 类型的项目创建文档时,它还将包含另一个项目 B 的所有属性。

最终结果是,当用户搜索在项目 B 上找到的数据时,用户在项目 A 上得到了点击。本质上,我想我正在尝试以编程方式“扩展”Lucene 文档。

到目前为止,这是我的代码。我正在扩展索引器类并覆盖一个方法,在该方法中我将字段从项目 B 添加到项目 A(上下文文档)。在我web.config的自定义数据库爬虫类中,我添加了一个特定的搜索索引(用于调试速度)。

public class DatabaseCrawlerExtension : Sitecore.Search.Crawlers.DatabaseCrawler
{
    protected override void AddAllFields(Lucene.Net.Documents.Document document, Sitecore.Data.Items.Item item, bool versionSpecific)
    {
        base.AddAllFields(document, item, versionSpecific);

        string fieldName;
        if (/* item is of template A */)
        {
            var targetItems = /* get items based on a property */;
            foreach (var additionalIndexItem in targetItems)
            {
                foreach (var fieldKey in additionalIndexItem.Fields
                    .Select(f => f.Key)
                    .Where(fk => !fk.StartsWith("_")))
                {
                    document.Add(base.CreateValueField(fieldKey, additionalIndexItem[fieldKey]));
                }
            }
        }
    }
}

我已经调试了这段代码,可以看到它到达了调用行document.Add,并添加了正确的数据。我尝试过的不同之处在于base首先或最后调用该方法,以及尝试使用该方法AddSpecialFields而不是AddAllFields. 这并没有在索引中产生任何额外的数据。

为了调试/查看索引,我一直在重建索引(在 Sitecore 中)并查看最终结果,以及使用名为Luke的工具直接查看生成的索引文件。

4

3 回答 3

1

CreateValueField是一种在文档中创建索引和未存储字段的便捷方法(根据sitecore文档)。. 我怀疑这是您遇到的问题。正如人们所预料的那样,当从索引中获取时,Luke 不会显示仅索引字段。

如所述,这听起来像是您使用的正确行为。您想在项目 B 中搜索值,并返回项目 A 中的值,因此不需要从搜索中返回项目 B 中的值。尝试测试从项目 B 中搜索值是否有效,而不仅仅是查看存储的字段。您也可以尝试按"Reconstruct & Edit",它可能能够构建一个包含未存储字段值的文档。

另一个可能的问题是您试图从项目 B 中包含的数据类型。 CreateValueField试图索引一个值,例如数字或日期。这些处理方式不同,我真的不知道它会如何处理文本值。如果您尝试包含文本值,则应使用CreateTextField, 代替。

于 2013-06-25T18:18:13.353 回答
1

这只是一个猜测,但base.CreateValueField()您可以尝试自己创建一个新的Lucene.Net.Documents.Field并将其添加到文档中,而不是使用 。如果你想用 Luke 看到索引中的值,一定要在 Field 上设置StoreField.Store.YES,否则,值会被索引,但不会存储在索引中。

于 2013-06-25T17:34:57.510 回答
0

下面是我的自定义媒体爬虫的代码。它适用于我并将自定义值添加到lucene索引。它不会执行base.AddAllFields,但这不应该是您的代码不起作用的原因。

public class MyMediaCrawler : Sitecore.Search.Crawlers.DatabaseCrawler
{
    protected override void AddAllFields(Document document, Item item, bool versionSpecific)
    {
        MediaItem mediaItem = item;

        document.Add(CreateField(Sitecore.Search.BuiltinFields.Content, item.DisplayName, true, 1f));
        document.Add(CreateField("anc", String.Join(" ", item.Axes.GetAncestors().Select(a => a.ID.ToShortID())), true, 1f));
        document.Add(CreateField("filename", String.IsNullOrEmpty(mediaItem.Title) ? item.DisplayName : mediaItem.Title, false, 1f));
    }
}
于 2013-06-26T08:17:55.620 回答