image

Rebuild the index for selected sites in Episerver Find | Admin Tool

image By - Ravindra Rathore
01 Oct 2019

Hi Guys,

Last Friday, I wrote a blog post related to “Reindex a target site in Find” using is works job. It works well but you need to update the site definition every time when you want to rebuild the indexes for any site.

So I received some feedback to convert it to Episerver Admin Tool and now I converted it to Episerver Admin Tool. Where you can rebuild the indexes for selected sites.

Here is the final structure of my solution.

To create a new GUI Plugin Episerver provide a template for Webforms but not for MVC so you need to create it manually. Below I mentioned the steps for creating a GUI plugin using MVC.

FYI – You can refer this blog post to create a custom GUI Plugin using MVC

Create a Controller

                                            
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Web.Mvc;
using EPiServer.Find.Cms;
using EPiServer.Find.Helpers.Text;
using EPiServer.PlugIn;
using EPiServer.ServiceLocation;
using EPiServer.Web;
using ReindexTargetSite_AdminTool.AdminTools.FindIndexPlugin.ViewModels;

namespace ReindexTargetSite_AdminTool.AdminTools.FindIndexPlugin
{
    [GuiPlugIn(
        Area = PlugInArea.AdminMenu,
        Url = "/custom-plugins/my-plugin",
        DisplayName = "Rebuild Find Index")]
    [Authorize(Roles = "CmsAdmins")]
    public class RebuildFindIndexController : Controller
    {
        public static string Message { get; set; }
        public static string ExecutionCompleteMessage { get; set; }

        private ISiteDefinitionRepository _siteDefinitionRepository;
        public RebuildFindIndexController(ISiteDefinitionRepository siteDefinitionRepository)
        {
            _siteDefinitionRepository = siteDefinitionRepository ?? ServiceLocator.Current.GetInstance();

        }
        public ActionResult Index()
        {
            var siteDefinitions = _siteDefinitionRepository.List();
            var siteList = new List();
            if (siteDefinitions.Any())
            {

                foreach (var site in siteDefinitions)
                {
                    siteList.Add(site);
                }

            }

            var model = new RebuildFindIndexViewModel
            {
                Sites = siteList
            };
            return View("~/AdminTools/FindIndexPlugin/Views/Index.cshtml", model);
        }

        [HttpPost]
        public async Task InitiateRebuildIndex(Guid[] selectedObjects)
        {
            Message = null;
            ExecutionCompleteMessage = null;

            string selectedSite = Request.Form["SelectedSite"];

            _ = Task.Run(() => StartRebuild(selectedObjects));
            return View("~/AdminTools/FindIndexPlugin/Views/Index.cshtml");
        }

        private void StartRebuild(Guid[] selectedSite)
        {
            foreach (var site in selectedSite)
            {
                SiteDefinition.Current = _siteDefinitionRepository.List().FirstOrDefault(i => i.Id.Equals(site));

                if (SiteDefinition.Current != null && !string.IsNullOrEmpty(SiteDefinition.Current.Name))
                {
                    var statusReport = new StringBuilder();

                    // ReIndex the indexes for the sites
                    ContentIndexer.ReIndexResult reIndexResult = ContentIndexer.Instance.ReIndex(
                        status =>
                        {
                            if (status.IsError)
                            {
                                string errorMessage = status.Message.StripHtml();
                                if (errorMessage.Length > 0)
                                    statusReport.Append($"{errorMessage}");
                            }

                            Message =
                                $"Indexing job [{(SiteDefinition.Current.Name)}] [content]: {status.Message.StripHtml()}";
                        },
                        () => false);
                }
            }

            ExecutionCompleteMessage = Message;
        }
        [HttpGet]
        public ActionResult GetMessage()
        {
            return Json(new { RunningMessage = Message, StopExecution = ExecutionCompleteMessage }, JsonRequestBehavior.AllowGet);
        }
    }
}
                                                

Create a ViewModel


using System;
using System.Collections.Generic;
using EPiServer.Web;

namespace ReindexTargetSite_AdminTool.AdminTools.FindIndexPlugin.ViewModels
{
    public class RebuildFindIndexViewModel
    {
        public IEnumerable SelectedSites { get; set; }
        public IEnumerable Sites { get; set; }
    }
}

Create a View


@using System.Web.Mvc
@using System.Web.Mvc.Html
@inherits System.Web.Mvc.WebViewPage
    @{
    Layout = null;
    }
    
    
    @if (Model != null && Model.Sites != null && Model.Sites.Any())
    {
    <h4>Site Listing</h4>

    using (Html.BeginForm("InitiateRebuildIndex", "RebuildFindIndex", FormMethod.Post))
    {

    foreach (var site in Model.Sites)
    {
    <input type="checkbox" title="@site.Name" name="selectedObjects" value="@site.Id">

    <label for="selectedObjects">@site.Name</label>
    <br />



    }
    @*@Html.DropDownList("SelectedSite", new SelectList(Model.Sites, "Value", "Text"))*@
    <input type="submit" value="Rebuild" />

    }
    }
    else
    {
    <h4 class="job-started">Schedule job started</h4>
    <div id="runningStatus"></div>
    }

Create an initialization Module


using System.Web.Mvc;
using System.Web.Routing;
using EPiServer.Framework;
using EPiServer.Framework.Initialization;

namespace ReindexTargetSite_AdminTool.AdminTools.FindIndexPlugin.Initialization
{
    [InitializableModule]
    [ModuleDependency(typeof(EPiServer.Web.InitializationModule))]
    public class PluginRouteInitialization : IInitializableModule
    {
        public void Initialize(InitializationEngine context)
        {
             RouteTable.Routes.MapRoute(
             null,
             "custom-plugins/my-plugin",
             new { controller = "RebuildFindIndex", action = "Index" });
             RouteTable.Routes.MapRoute(
                 null,
                 "custom-plugins/my-plugin/initiate-rebuild-index",
                 new { controller = "RebuildFindIndex", action = "InitiateRebuildIndex" });
             RouteTable.Routes.MapRoute(
                 null,
                 "custom-plugins/my-plugin/get-message",
                 new { controller = "RebuildFindIndex", action = "GetMessage" });
        }

        public void Uninitialize(InitializationEngine context)
        {
            //Add uninitialization logic
        }
    }
}

That’s it from a code point of view. Now you just need to login into you Episerver and go to Admin view and select the new plugin “Rebuild Find Index“

Now select the sites and click on the “Rebuild” button.

It will rebuild the indexes for the selected sites.

Thanks for reading this blog post I hope it helps

Thanks and regards

Ravindra S. Rathore