我正在为客户的Sitecore项目之一开发全局搜索查询。要求通过2种方式进行搜索
1.与搜索关键字和标题完全匹配。(第一优先级)
1.必须拆分搜索关键字,并检查是否每个吐出的关键字都存在于标题中。(第二优先级)
我使用Sitecore.ContentSearch.Linq中的predicatebuilder并开发了以下代码。我使用了Boost方法来设置优先级,它工作正常
private Expression<Func<GlobalSearchResultModel, bool>> GetSearchResultsPredicate(string keyword)
{
var finalPredicate = PredicateBuilder.True<GlobalSearchResultModel>();
var searchKeywordPredicate = PredicateBuilder.False<GlobalSearchResultModel>();
var splittedKeywordPredicate = PredicateBuilder.True<GlobalSearchResultModel>();
if (!string.IsNullOrEmpty(keyword))
{
var searchKeyword = keyword;
var splittedKeywords = searchKeyword.Split(' ').Take(10).ToList();
ID homeTemplateId = Templates.GlobalSearch.HomeTemplateId;
ID announcementListingId = Templates.GlobalSearch.AnnouncementListingId;
finalPredicate = finalPredicate.And(x => (x.Paths.Contains(homeTemplateId)
|| x.Paths.Contains(announcementListingId)
)
&& x.LatestVerion && !x.ExcludeFromSearch
&& !(String.IsNullOrEmpty(x.Title) && String.IsNullOrEmpty(x.AnnouncementTitle)));
searchKeywordPredicate = searchKeywordPredicate.Or(x => x.Title.Equals(searchKeyword).Boost(5f));
foreach (var splittedKeyword in splittedKeywords)
{
splittedKeywordPredicate = splittedKeywordPredicate.And(x => x.Title.Contains(splittedKeyword).Boost(3f));
}
finalPredicate = finalPredicate.And(searchKeywordPredicate.Or(splittedKeywordPredicate));
}
return finalPredicate;
}
字符串
使用以下命令检索结果
var result = context.GetQueryable<GlobalSearchResultModel>()
.Where(GetSearchResultsPredicate(searchKey))
.ToList();
型
现在,我需要按boosting上的日期字段对它们进行排序。就像从Boost(5 f)返回的项一样,将按它们的UpdatedDate降序排列。但在应用升压后,即使是相同的升压项目,我有不同的分数,这是预期的。我需要一个恒定的分数相同的提升值,这样我就可以order的UpdatedDate后,按分数排序。我在Solr查询中看到^=
关键字用于常量评分。有没有办法使用Sitecore.ContentSearch.Linq
来应用它?我想在不做任何内存操作的情况下实现它。
感谢您提供解决方案/建议。
1条答案
按热度按时间qnzebej01#
恐怕用
Sitecore.ContentSearch.Linq
和对Solr的单个请求是不可能实现这一点的。我必须说,对于网站用户和内容编辑来说,结合了提升和自定义排序的复杂逻辑通常是令人困惑和难以理解的。但是如果你确实想实现这个场景,最好的方法是将它分成两个Solr查询:
1.获取精确匹配结果并按
UpdatedDate
排序。字符串
1.获取其余的结果,根据需要对它们进行排序(或保留默认的分数排序),并附加到第一个结果集:
型