Как вывести новый контент в верхнюю часть результатов поиска с помощью Umbraco Examine? - PullRequest
0 голосов
/ 04 октября 2018

У нас есть сайт, созданный в Umbraco CMS, и я занимаюсь поиском по сайту.На сайте есть раздел под названием «Новости», где регулярно публикуются обновления.При выводе результатов из раздела новостей (среди других страниц) я хочу, чтобы результаты отображались как можно раньше, например, если кто-то ищет «результаты экзамена», я хотел бы привести соответствующие страницы новостей, созданные в 2018 году раньше, чем страница, созданная ранее.в 2017 году и тд.Если есть способ повысить (либо время запроса, либо время индекса), чтобы увеличить последние страницы?

Ниже мой код, который я написал до сих пор:

var page = 1;
var pageSize = 5;

if (Request.QueryString["q"] != null)
    searchQuery = Request.QueryString["q"];

if (Request.QueryString["page"] != null)
    Int32.TryParse(Request.QueryString["page"], out page);

ISearchResults searchResults = null;
BaseSearchProvider searcher = ExamineManager.Instance.SearchProviderCollection["ExternalSearcher"];

var headerFields = new[] { "contentTitle", "metaTags", "metaDescription", "nodeName" };
var contentFields = new[] { "contentDescription", "mainBody" };
var criteria = searcher.CreateSearchCriteria(IndexTypes.Content, BooleanOperation.Or);
var searchTerm = string.IsNullOrEmpty(Request["q"]) ? string.Empty : Request["q"];

if (searchTerm != string.Empty)
{
    searchTerm = searchTerm.MakeSearchQuerySafe();

    if (searchTerm.Length > 0)
    {
        searchTerm = searchTerm.Trim();
    }

    var examineQuery = criteria.GroupedOr(headerFields, searchTerm.Boost(100));
    examineQuery.Or().GroupedOr(contentFields, searchTerm.Boost(50));

    if (searchTerm.Contains(" "))
    {
        examineQuery.Or().GroupedOr(headerFields, searchTerm.RemoveStopWords().Split(' ').Select(x => x.MultipleCharacterWildcard().Value.Boost(10)).ToArray());
        examineQuery.Or().GroupedOr(contentFields, searchTerm.RemoveStopWords().Split(' ').Select(x => x.MultipleCharacterWildcard()).ToArray());
    }

    searchResults = searcher.Search(examineQuery.Compile(), maxResults: pageSize * page);
}

1 Ответ

0 голосов
/ 09 октября 2018

Поскольку другие могут столкнуться с той же проблемой и получить доступ к этому вопросу (через поиск), я публикую ответ на свой вопрос.

Я написал два обработчика событий, как показано ниже:

  1. Всякий раз, когда в Umbraco CMS публикуется новое содержимое, запускайте перестроение индекса Examine.
  2. Когда индексатор Examine встречает псевдоним типа документа как "newsArticle", повышайте значение документа относительно последней обновленной даты.

Код обработчика событий приведен ниже:

public class ExamineEvents : Umbraco.Core.ApplicationEventHandler
{
    protected override void ApplicationStarted(UmbracoApplicationBase umbracoApplication, ApplicationContext applicationContext)
    {
        var indexer = (UmbracoContentIndexer)ExamineManager.Instance.IndexProviderCollection["ExternalIndexer"];
        indexer.DocumentWriting += Indexer_DocumentWriting;
        Umbraco.Core.Services.ContentService.Published += ContentService_Published;
    }

    private void ContentService_Published(Umbraco.Core.Publishing.IPublishingStrategy sender, Umbraco.Core.Events.PublishEventArgs<Umbraco.Core.Models.IContent> e)
    {
        ExamineManager.Instance.IndexProviderCollection["ExternalIndexer"].RebuildIndex();
    }

    private void Indexer_DocumentWriting(object sender, DocumentWritingEventArgs e)
    {
        //if it is a 'news article' doc type then > BOOST it DOWN - the older the article, the lower the boost value 
        if (e.Fields.ContainsKey("nodeTypeAlias") && e.Fields["nodeTypeAlias"] == "newsArticle")
        {
            float boostValue = 1f;
            const string umbDateField = "updateDate";
            if (e.Fields.ContainsKey(umbDateField))
            {
                DateTime updateDate = DateTime.Parse(e.Fields[umbDateField]);
                var daysInBetween = Math.Ceiling((DateTime.Now - updateDate).TotalDays + 1); // +1 to avoid 0 days
                boostValue = (float) (1 / daysInBetween);
            }
            e.Document.SetBoost(boostValue);
        }
    }
}
...